Upcasting ServiceContract - c#

I have a WCF service, which exposes many methods.
My application consumes this service, and ServiceContract includes OperationContract definitions for only some of methods.
To cut to the question, consider following code example:
[ServiceContract]
public interface IServer
{
[OperationContract]
void BasicOperation();
}
[ServiceContract]
public interface IExtendedServer : IServer
{
[OperationContract]
void ExtendedOperation();
}
I would like to make contracts so that application has extension capability. In other words, I'd like to be able to use IServer contract everywhere, but to allow plugin-like architecture to extend basic contract interface, so that plugin itself can call ExtendedOperation() operation contract.
So, how do I structure my code, or, what changes do I have to make, in order to be able to do something like following? (channel is of type IServer)
((IExtendedServer)channel).ExtendedOperation()
When I attempt to do this, I get error
System.InvalidCastException : Unable to cast transparent proxy to type 'Contract.IExtendedServer'.
I hope I wasn't confusing...

Services in a SOA world need to have a well-defined and pretty static interface. SOAP services require a representation in a WSDL (and included or separate XSD = XML schema for the data involved).
I don't see how you can create something like a plug-in system in a service world. Plugins work great on a local app - load your resources, language extensions, graphics filters - whatever strikes your fancy. But in a SOA world, this "agility" is the exact contrary of what you're trying to do - create and offer well-defined, fully specified services to be used.
The only option I could see is using a REST-based approach, since there you don't really have many of those limitations. Normally I say this lack of a formal service description is one of the major drawbacks and weak points of REST, but since using REST, the operations are really just defined by the URL's used, this might be a plus in your case.
So I would say: if you really want flexibility in services, you need to check out REST based services. SOAP doesn't fit that bill. Go to the WCF REST Developer Center on MSDN for a vast array of information and resources on how to use REST in and with WCF.

I'm not sure what you're trying to accomplish here. You're dealing with services, which have endpoints exposing specific contracts (i.e. interfaces). You're not dealing with objects and casting and the like; it won't work and isn't the right approach anyway.
The way I see it, what you have is indeed just that: A service that exposes one endpoint with a set of common operations, and potentially X number of additional endpoints with other contracts with extension operations. You could still have a single service class on the service side, but as far as the client goes, they are simply different endpoint/services.

Related

Q: How to build the most basic service aggregation pattern?

I have a set of services I want to be able to access via one end point altogether.
Now I want to build something in wcf rather than use an existing framework/software so that is out of the question.
Suppose I have 10 contracts each representing a contract of an indepedent service that I want to "route" to, what direction should I go?
public partial class ServiceBus : ICardsService
{
//Proxy
CMSClient cards = new CMSClient();
public int methodExample()
{
return cards.methodExample();
}
So far I've tried using a partial class "ServiceBus" that implements each contract but then I have more than a few (60+) recurrences of identical function signatures so I think I should think in a different angle.
Anyone got an idea of what I should do? or what direction to research? currently I'm trying to use a normal wcf service that's going to be configured with a lot of client end points directing to each of the services it routes TO - and one endpoint for the 'application' to consume.
I'm rather new at wcf so anything that may seem too trivial to mention please do mention it anyway.
Thanks in advance.
I have a set of services I want to be able to access via one end point
altogether.
...
So far I've tried using a partial class "ServiceBus" that implements
each contract
It's questionable whether this kind of "service aggregation" pattern should be achieved by condensing multiple endpoints into an uber facade endpoint. Even when implemented well, this will still result in a brittle single failure point in your solution.
Suppose I have 10 contracts each representing a contract of an
indepedent service that I want to "route" to, what direction should I
go?
Stated broadly, your aim seems to be to decouple the caller and service so that the caller makes a call and based on the call context the call is routed the relevant services.
One approach would be to do this call mediation on the client side. This is an unusual approach but would involve creating a "service bus" assembly containing the capability to dynamically call a service at run-time, based on some kind of configurable metadata.
The client code would consume the assembly in-process, and at run-time call into the assembly, which would then make a call to the metadata store, retrieving the contract, binding, and address information for the relevant service, construct a WCF channel, and return it to the client. The client can then happily make calls against the channel and dispose it when finished.
An alternative is to do the call mediation remotely and luckily WCF does provide a routing service for this kind of thing. This allows you to achieve the service aggregation pattern you are proposing, but in a way which is fully configurable so your overall solution will be less brittle. You will still have a single failure point however, unless you load balance the router service.
I'm not sure about making it client side as I can't access some of the
applications (external apis) that are connecting to our service
Well, any solution you choose will likely involve some consumer rewrite - this is almost unavoidable.
I need to make it simple for the programmers using our api
This does not rule out a client side library approach. In fact in some ways this will make it really easy for the developers, all they will need to do is grab a nuget package, wire it up and start calling it. However I agree it's an unusual approach and would also generate a lot of work for you.
I want to implement the aggregation service with one endpoint for a
few contracts
Then you need to find a way to avoid having to implment multiple duplicate (or redundant) service operations in a single service implementation.
The simplest way would probably be to define a completely new service contract which exposes only those operations distinct to each of the services, and additionally a single instance of each of the redundant operations. Then you would need to have some internal routing logic to call the backing service operations depending on what the caller wanted to do. On second thoughts not so simple I think.
Do you have any examples of a distinct service operation and a redundant one?

WCF single point-of-contact

WCF beginner's question: I've been told that changing the WCF contract is costly and requires constant maintenance (recreating the proxy in the client side), and therefore the preferred method is having one very generic point-of-contact method (which decides how to act, say, according to a given enum parameter).
This sounds quite smelly to me, but I haven't been able to find any information about this issue (bad choice of search keywords? probably).
Any advice, or maybe a useful link?
Thanks!
You don't need to generate the proxy again, you can simply ensure the client is built with the correct interface version. If you're very careful and only add methods, not remove or modify, that works just fine too. That's a lot of responsibility to manage, of course.
To use an interface rather than generate a client proxy, check my question from a while ago:
WCF Service Reference generates its own contract interface, won't reuse mine
You are confusing some terms here and I think you might be referring to a known flaw which has been fixed in .Net 3.5 SP1.
Recreating the WCF proxy used to be an expensive operation at runtime. This has been improved in .Net 3.5 to cache the proxy objects transparently MSDN Blog.
If you are referring to the "code maintenance" of the proxy, then all you are referring to is implementing an interface at the client. If you need to maintain the interface then this comes back to basic SOA. If your services provide access and as much information as possible, assuming that your service will be used for purposes you haven't yet considered then you will likely not need to modify the interface after it is created. You should also consider your upgrade paths as well.
Juval Lowy has a good discussion about this problem in his book which is a little dense but has some pretty good information in it.
A piece of advice: WCF has a whole lot of features designed to make your code really simple and elegant. If you are worreid about maintenance, what you may be driven to do is write an interface:
string ServiceMethod(string xml) //returns XML
Don't do this. Take the time to design a good maintainable interface and a good data/message contract. This will let WCF provide all the extras you get for free when hosting your service for interaction.
Generic (as in non-specific, monolithic) interfaces are hard to understand and program to. The reason not to define a single method as the API is that it's impossible for clients to understand what's going on, and when you change the (implicit) API of this interface, your clients will break in horrible ways that you won't detect at compile time.
It's been a while since I touched WCF, but if your clients are internal (same codebase, versioning and deployment schemes), then regenerating the WCF proxies is very easy, and having a "strong" detailed API will make your life so much easier than a generic one.
It depends on what kind of change you mean. Change to the service contract is indeed costly and should not happen. Service contracts are (or should be) at a sufficiently high level of granularity that change is very rare.
More common are changes to the types which are exposed on the service. These changes are more common and therefore you do need to approach your change in such a way as to avoid breaking existing clients if possible.
There are several ways you can do this, such as exposing your types polymorphically using an interface, but the simplest way is to simply ensure that changes to your types on add new data member fields and make the new fields non-mandatory. If you can limit your changes to these then this is has the lowest impact to existing clients and enables new clients to use the new fields.
Hope this helps.
This is true that modifying the service contract (interface) would also required the client to recreate the proxy class at their end using the new published WSDL and may even require the client to change their code as par the new proxy. I don't think you can create such a generic interface that can handle all changes further down the road in the contract. A contract has to be written very carefully so that it doesn't change often and if there is a need to change the contract then it is better to deploy the service with a different version so that your old client can still work with the old version.

In WCF, is there a way to omit / hide a ServiceOperation or a DataMember from the WSDL?

I have an existing WCF service. At some point, sometimes an [OperationContract] or a [DataMember] in a data contract becomes [Obsolete]. I don't want to remove the method, for back-wards compatibility reasons. Another example is sometimes I have an Enum, and want to [Obsolete] one of the choices, but I can't completely remove it because items already exist in the system / database that contain that value.
Anyway, is there a way to omit certain items from the generated WDSL? For example:
[ServiceContract]
public interface IMyService
{
[OperationContract]
string SomeMethod(string x); // I do want this in the WSDL
[Obsolete]
[OperationContract]
string OldMethod(string x); // I do NOT want this in the WSDL, but I do want it to still work / be callable if an older system tries to call it.
}
There isn't anything out-of-the-box which can be used to do that, but you can use a WSDL export extension to remove some of the operations from the service metadata. I implemented a sample for this scenario at http://blogs.msdn.com/b/carlosfigueira/archive/2011/10/06/wcf-extensibility-wsdl-export-extension.aspx.
WCF is pretty versioning tolerant within some constraints as documented in this MSDN article. It's probably too late for your current service to adopt some of these practices but you can accomplish what you want by creating new ServiceContract interfaces that remove the operations and enums you need hidden.
You would also need to create a new endpoint for the new the interface. The same service implementation can support multiple interfaces with a little tweaking so the changes shouldn't be too extensive. Any new clients would use the new service endpoint while the the old clients would use the original endpoint.

How does WCF turn a ServiceContract/OperationContract into a Message that can be serialized?

I'm starting to experiment with using ActiveMQ (in conjunction with the ActiveMQ.NMS bindings) to support some cross platform RPC messaging that we're looking at doing.
As part of this I'd like to be able to define our RPC contracts in the manner WCF provides - eg.
[ServiceContract]
public interface IUsers
{
[OperationContract]
IEnumerable<IUser> void GetByEmail(string email);
}
And I'm looking at contributing to the ApackeMQ.NMS.WCF project to allow this to work, and I have some experience at writing custom bindings so I'm away with that.
However, I'm having trouble with a conceptual issue first with how WCF operates. Obviously at some level a call through a proxy on a client channel for "GetByEmail" must get converted into message and response objects so that they can be serialized. I'd like to be able to know how this works to get a better overall understanding of WCF.
I am unable to find any documentation as to exactly how that is done and indeed which classes within the fairly hefty WCF infrastructure are involved.
Has anyone got any pointers? A top level explanation and/or directions to the classes would be brilliant.
Thanks.
There is a step before that: How (what format) to use for the serialization?
WCF connects through Bindings, and the configuration of the binding picks a format/protocol.
And 'how' the command is transferred for each protocol? I don't know and I don't think it will be very helpful to dig into that (low level) stuff.

WCF - Single Web Service Endpoint Using Partial Classes

A project I am working on requires a structure as such:
{BasePrefix}/Application/{id}/Security/Users/{userId}
{BasePrefix}/Application/{id}/Objects/{objectId}
etc.
Application.svc would be end up being my WCF Web Service. I tried to convince them to do:
{BasePrefix}/Security/Application/{id}/Users/{userId}
This would allow me to have multiple WCF Web Services as Security.svc, Objects.svc, etc.
They still want it all under application so instead of throwing all my service methods into a single file, I wanted to break it out by functionality and use partial classes to combine it all into one resource.
I saw an article about how to do this here: http://www.meineck.net/2008/04/wcf-hosting-multiple-wcf-services-as.html
The developer in that article is working with a Net TCP binding, however, so I am not sure if this will work with a WebHttpBinding and how IIS will handle the multiple resources.
Has anyone done this? Is the article I linked a good resource? Or is there a better alternative method to achieve the same results?
The methodology in the linked article is sound, and will work for bindings other than netTcpBinding (including webHttpBinding, wsHttpBinding and so on).
However, I believe what you are trying to do is use a URL rewriting scheme (probably using the UriTemplate property), which is subtly different from what that article actually talks about. It is referring to the creation and implementation of multiple interfaces, by the same service, and mapping each interface to its own endpoint.
The approach does not work with a single endpoint. So if your endpoint is {BasePrefix}/Application, that can only be mapped to one interface (say IApplicationService) in the configuration.
In your case, I don't think you'll be able to go the multiple-interface route because you need to have just one endpoint. So you'll still need a single monolithic interface with all of the methods (ugly), but you could in theory use partial classes to split up the implementation of those methods into logical groups. It's better, but not exactly ideal.
You were on the right track with your original assessment. If your scheme looked like:
{BasePrefix}/Security/Application/{id}/Users/{userId}
{BasePrefix}/Repository/Application/{id}/Objects/{objectId}
Then you would be able to use either of the approaches - either have multiple services, or have a single service that implements multiple interfaces and hosts multiple endpoints.
What the code/configuration in that article is really designed to do is enable a single service instance to host multiple endpoints. The main reason to do this is if you would otherwise have to duplicate a lot of code between services. Unfortunately that's not your goal here, so you will either have to push harder for your proposed URI scheme, or deal with a monolithic service contract (interface) and do the best you can to keep the implementation clean through #region directives and/or partial classes.

Categories

Resources