So I have a layered application that I am adding a WCF service interface on top of. The service is simply a facade with all of our business logic already existing in Business Objects (BOs) within the Business Logic Layer (BLL) which is a class library. Within the BLL we use constructor injection to inject dependencies into the BOs. This is all working with good unit testing, etc. On to the problem...
Ordinarily I'd simply create a set of Request/Response objects as DataContracts for each service method with the appropriate properties for the operation. If the operation required one of our "entities" to be passed either to or from the method, I'd simply define a property of that type and everything would be fine (all of our BOs are serializable). However when one of these "entities" is passed into a service method, WCF deserializes the object without ever invoking the constructors we've defined and, as a result, the dependencies don't resolve.
Let's use the case of a service method called CreateSomething. I'd normally define this as a service operation with a signature like:
CreateSomethingResponse CreateSomething(CreateSomethingRequest request);
CreateSomethingRequest would be a DataContract and have amongst its properties a property of type Something that represented the "entity" being passed into the service. Something, in this case, is a business object that expects to receive an instance of the ISomethingRepository interface from the DI container when instantiated - which, as I said above, does not happen when WCF deserializes the object on the server.
Option #2 is to remove the Something property from the DataContract and define each of the properties explicitly in my DataContract then inside my service method, create a new instance of the Something class, letting the container inject the dependency, then map the property values from the DataContract object into the BO. And I can certainly do that but I am concerned about now having two places to make changes if, say, I want to add a property to the Something type. And, with a lot of properties, there's a lot of code duplication.
Has anyone crossed this bridge and, if so, can you share your thoughts and how you have or would approach this situation in your own applications? Thx!!!
There are two answers on your problem:
First: Do not send your entities and use data transfer objects instead. Your entities are business objects with its logic and data. The logic of business objects is most probably used to control the data. So let the business object control its data in business layer and exchange only dummy crates.
Second: If you don't want to follow the first approach, check documentation of your IoC container. There are ususally two methods for resolving dependencies. For example Unity offers:
Resolve - builds new instance and injects all dependencies (necessary for constructor injection)
BuildUp - takes existing instance and resolves all property dependencies. This should be your choice.
Thanks, Ladislav, for your answer as you confirmed what was already in my head.
What I ended up doing was to change my approach a little. I realized that my use of a business object, per se, was overkill and unnecessary. Or perhaps, just misdirected. When evaluating my requirements, I realized that I could "simplify" my approach and make everything work. By taking each logical layer in my application and looking at what data needed to pass between the layers, I found a design that works.
First, for my business logic layer, instead of a business object, I implemented a Unit of Work object: SomethingManager. SomethingManager is tied to my root Something entity so that any action I want to perform on or with Something is done through the SomethingManager. This includes methods like GetById, GetAll, Save and Delete.
The SomethingManager class accepts two objects in its constructor: an IValidator<Something> and an ISomethingRepository. These will be injected in by the IoC container. The former lets me perform all of the necessary validation using whatever framework we chose (initially the Validation Application Block) and the latter gives me persistance ignorance and abstracts the use of Linq-to-SQL today and makes upgrading to EF4 much easier later on.
For my service layer, I've wired the IoC container (Unity in this case) into WCF so the service instance is created by the container. This allows me to inject an instance of ISomethingManager into my service. Using the interface, I can break the dependency and easily unit test the service class. Plus, because the container is injecting the ISomethingManager instance, it is constructing it and will automatically resolve it's dependencies.
I then created DataContracts to represent how the data should appear when transferred across the wire via the service. Each Request/Response object contains these DataContracts as DataMembers rather than referencing my entity classes (or BOs) directly. It is up to the service method to map the data coming from or going to the Business Logic Layer (via ISomethingManager) - using AutoMapper to make this clean and efficient.
Back in the data layer, I've simply extended the generated entity classes by defining a partial class that implements the desired interface from the BLL. For instance, the Something L2S entity has a partial defined that implements ISomething. And ISomething is what the SomethingManager (and ISomethingManager interface) and ISomethingRepository work with making it very easy to query the database and pass the L2S entity up the chain for the service layer to consume and pass on (without the service layer having any knowledge or dependency on the L2S implementation).
I appreciate any comment, questions, criticisms or suggestions anyone has on this approach.
Related
I have a few questions about "best practices" in my application structure. I make use of skinny models, and have service layers which do most (all) of the database interaction. The models call the service layer when they need a database transaction.
I also have a factory class which can return forms, models, and service layer classes. This factory class may also return a "search" class which acts as a very simple DBAL and is used by my service layer.
This search class has helper methods such as getAll() and getById().
I'm slightly confused about which parts of my application should have access to the search class; currently my model uses the static factory to build the search class when it needs to retrieve an entity by it's ID. Should my models instead be calling my service layer to make this call, thus negating the need to use my factory class to return the searcher?
I guess I don't like the idea that my database can potentially be accessed from multiple parts of my application, when really I'd rather everything need to go through my service layer first.
Tips and feedback are much appreciated!
I would end up creating a SearchService (which implements an interface i.e. ISearchService) class which the model, or any other code, that wants to access the Searcher would interact with.
This way you keep a clear separation from the Searcher class, or factory, which could change in the future. The other benefit is that, by having all the search related code in the SearchService, it becomes a lot easier for devs to understand the code, since they know that search related code is in the SearchService, rather then dotted around the codebase, calling factory methods, etc.
Also, by using an ISearchService, you allow yourself the option to use Dependency Injection, which is a nice way of having your object initialised for you, and not having to worry about implementation changes.
That's just my preference though, rather then this being a right/wrong way to do things.
I am using Castle Windsor.
I have two component types where the implementation can be selected at runtime on a GUI. To handle this, I am resolving them by name. To handle resolving them by name, I am using the Typed Factory Facility.
One of the component types depends on the other. To handle the dependency, I am passing the argument as a factory method/constructor parameter argument.
Here is a redacted and abridged version of this factory interface:
public interface IModelFactory
{
IMyDomainCommandFactory GetFooCommandFactory();
IMyDomainCommandFactory GetBarCommandFactory();
IMyDomainStrategy GetCreateSpecificSizeStrategy(int size, IMyDomainCommandFactory commandFactory);
IMyDomainStrategy GetCreateUntilFailureStrategy(IMyDomainCommandFactory commandFactory);
}
Note that I am using my own implementations for IMyDomainCommandFactory, rather than using the Typed Factory facility. Those factories have intentionally complex behavior, and the facility doesn't suit their needs.
The problem I am noticing is that if I register my strategy components with a singleton lifestyle, I always get back the same instance, even if I pass different arguments to the getter.
In my opinion, this goes against the Principal of Least Astonishment, but maybe other people have a different opinion :) Should this be considered a bug?
If not, is there a clean way to get the container or factory to create only one instance per argument combination?
Depending how you look at it, but certainly instance per combination of parameters can't be called a singleton so I say it would go against PoLA if Windsor did implement the behavior you'd expect.
If you want it, you need a custom, non-singleton lifestyle.
My understanding is that all contract-implementing code has to be in a single class, that can become very large, obviously. How do I avoid this? I really prefer to have a few small classes doing one part of the communication with clients than a single behemoth class.
The only idea I could think of is using multiple interfaces implemented by a single class split up by partial, but I don't think this is really solving the issue.
You might want to use Inheritance, depending on the structure of yoru code. Usually you can break all code up into smaller pieces, helpers, sub-routines, etc.
It's like with any other API-development, you don't want / don't need everything in the same place in the same package.
First, if your contract is big, can they be refactor into more specific service contracts?
The contract implementation class can be implemented as entry point method. You can always model the implementation and define the appropriate abstraction and have your service contract implementation class calls those internal implementation.
If you could change your code fundamentally, you could expose just a single endpoint that works with request/response messages. This way there could be a single end-point and a single service definition that takes a (possibly derived) request message and returns a response message. Your interface into the service would then just be a single method and in the server side implementation you would route that request object to the actual service implementation (possibly determined by a factory) possibly using metadata on the request message (or even it' type-name) to define what service is being called.
So, your end service interface would just have a method like this:
public interface IServiceRequestor
{
Response ProcessRequest(Request request);
}
This allows you to handle a possibly unlimited number of exposed services without having to know what they will be at compile/dev time, and also avoid a proliferation of Service methods defining the service calls available
That 'single class' usually is a facade, just a communication front-end.
So you should not implement all your logic in the Service implementor.
And your interfaces should be as small as possible (do 1 thing well). But if necessary your facade can call on multiple classes.
We have about 60 partial files called "BeamServer.cs", each in a sub-folder that corresponds to the purpose of the functions in that file. Any helper classes (or other helper files) that are for the same area of our program resides in that folder as well.
Your "one class" represents your "one business need". We found a nice side benefit in that if one of the members of our team is working on the "Accounting" portion of BEAM (our software), then they would check out the file "Accounting\BeamServer.cs" and none of the rest of the team would be effected.
EDIT: Also, the class should only contain the method signatures (and wrapper functions that simply call base.Channel.DoSomething()... Any data structures would of course be their own class files (such as "Person.cs" or "Employee.cs" or whatever).
Problem:
WCF contract objects cannot implement 2 types of lists (ie: List and List).
Long-winded explanation:
I'm building a WCF service on top of an existing core system, and I'm trying to work out the best way to implement some of my business objects.
The core system utilizes interfaces for all business objects - Person management functionality, for instance, requires that I pass in an object which implements IPerson. Nothing out of the ordinary here.
The goal is to have a contact object (Person) which can be used on the service side of things, and also implements IPerson so that it can be passed into the core without requiring a conversion layer. This all works just fine for items like Person.
The issue comes in for lists: a method in the core, for instance, might require a IPersonList to be passed in, and as anyone who's dealt with inherited generics will know, List does not inherit from IList.
In our currently running ASMX service, we implement this with some up/down casting in the web objects. "WebPerson" will inherit from List, and implement IList explicitly so that the IList properties do not show up on the WSDL.
In WCF, however, if you try to use this same object, you will get the following error:
Type 'Cssi.IBroker.Service.Cssi.Contracts.PersonList' with CollectionDataContractAttribute attribute is an invalid collection type since it has multiple definitions of interface 'IList`1'.
Apparently, now that the new WCF serializer knows how to serialize IList, it's no longer able to ignore the second explicit implementation.
If possible, I'd like to avoid creating a PersonList object just for the contracts and then converting to and from an IPersonList object for each call. Changing the core business logic to use concrete objects designed just for the WCF services isn't an option.
Help!
I ended up deciding the best route was a set of dedicated objects used only for the contracts. With them being dedicated to one task, I was able to keep them cleaner without having to compromise my internal design for the sake of the WSDL. For the WSDL objects themselves, I ended up using arrays instead of IList.
The extra step of conversion is a bit cumbersome, but less than trying to keep my core objects WCF friendly would be.
I know there have been similar questions on this topic but I wasn't completely sure they were solving the same problem. So just to be clear...
I have an existing class library that has namespaces for types, business logic and data access. The classes in the logic and data access namespaces are static and have basic crud methods to fill the type instances with data or take type instances that are already full and do inserts or updates in the database.
Now, in addition to the existing applications that reference this library directly, I want to also create a WCF service so that other applications can consume the objects and methods that way.
Every WCF turorial that I see creates the domain objects in the service project - but I don't want my objects defined in two places.
So I was thinking I could reference serialization in my existing class library and mark the type classes as [DataContract] and the properties as [DataMember]. Then, in the WCF project, create the [ServiceContract] interfaces with [OperationContract] methods to match the static logic classes and methods from the existing library that I want to expose. Then, from the WCF project, reference the existing class library and implement the WCF interfaces by having methods in it that call the existing library logic methods which return the existing library types.
Is this a good pattern?
It sounds good but retrofitting serialization tends to be more trouble than it seems at first. I would suggest that you build some lightweight data contracts into a service layer and then build a small tier that sits between your service layer and the business layer to translate the data contracts into business objects and vice-versa.
Assuming your business object can be serialized (have attribute Serializable) one approach could be creating DataContainer object, which will be your data contract. This object would be used in your CRUD methods.
For example your interface could be
Update(DataContainer obj)
Insert(DataContainer obj)
etc.
Then you would use Binary serialization to pack your object into array of bytes and pass it this way through WCF. On the other side you would deserialize them using again BinarySerialization. You just have to make sure that both sides (client and server) have valid version of assembly with your business objects types.