Distributing domain entities over the wire
When we design our domain entities we don’t have a
presentation layer or database in mind. The domain entities
are core business objects located on the server or client
side based of what kind of application we are building.
Domain entities aren’t designed for distribution. When we
realize that we need a distribution, we shouldn’t distribute
the entities, instead collect the data we need to distribute
and create a data transfer object (DTO) instead. Have the
network in mind, a domain entity aren’t designed with a
network in mind and of that reason not suitable for
distribution. When we create our domain entities, they
aren’t designed for presentation purpose, they are designed
to fulfill business needs. You should be careful when you
start thinking about returning a domain entity to the View
when using a patterns like MVC, instead use DTO or a
ViewModel, because once again the domain entities aren’t
designed with presentation in mind, and aren’t often
suitable for presentation purpose. It’s often better to map
them to a DTO or ViewModel, objects that are suitable for
presentation purpose or passed over the wire.
I often see demos and example codes where models are generated out from a database. Remember it you do that, your application’s design is driven by a relational database schema, do you really want a database to set the limit in your application design? I don’t. Developers are good at one thing, implementing business logic, that is what they do, that is what they are good at, that is what they should focus on (if we live in the perfect world ;)). We should work against our model. We shouldn’t care about how the database schema looks like. A database is a way to store information, and we have database administrator that are experts in the database area, let them handle the database schema and together with developers map the domain model to the database schema, with the use of an ORM, like Entity Framework 4.0 or nHibernate etc.
When it comes to WCF or Web Services, never distribute
the domain entities, they aren’t designed for that kind of
purpose in the first place(if we don’t use Distributed
Domain Driven Design). There is a reason why we call the
data sent from a Service as a message. A message is created
with network in mind, that is why we use data contracts.
When it comes to .NET RIA Services, don’t distribute the
Entity Framework generated object or LINQ to SQL, they are
generated out from a database schema, and it’s so easy to
select whole tables and related tables to get what we want
and then we distribute it and forget about the network
between the client and server. In some cases we don’t even
want to think about the network existence because it adds
limit to the information and how we would like to work with
objects. But we can’t hide the complexity how much we try,
we have to realize that we do have a network, and have that
in mind when we design our RIA. We can still on the
server-side create our perfect domain model, but we
shouldn’t distribute it. Instead transform peace of it into
DTOs and only make sure we send the data we are needed. I
have seen several examples where developers generate codes
from Entity Framework or LINQ to SQL and returns it with
.NET RIA Services. When I look at the examples I can see big
object graphs passed over the wire and developers are using
it as it was local objects, they start to requesting about
Lazy Loading support in .NET RIA Services etc. Either they
forgot about the network, or they have lack of experience.
For intranet, small database driven applications it can be
ok to create a model out from a database schema and
distribute it with .NET RIA Services, they don’t often even
use business logic, and they don’t need a domain model. But
when it comes to large application it’s not often an good
idea to generate object out from a database schema and
distribute it. In that case DTO is much better option. Not
only to limit the data passed, but also because of
separation of concerns. The best thing with .NET RIA
Services is that it does support DTOs :) Microsoft are good
at creating frameworks for developers, but sometimes they
want to satisfy everyone, and that often leads to people
will use the frameworks in a wrong way. WCF is probably one
of the better technologies made from Microsoft, they have
learned from the fail of DCOM. When we use WCF we have to
create a data contract, which force us to think about what
we are distributing, they have also add a small limit of how
much data we can by default pass over the wire. I know that
some developers think WCF is complex to use and not so easy
to learn, but sometimes it shouldn’t be easy to create
things that are complex, the complexity is there by some
reasons, and it can’t be hidden.