Is automapper preventing lazy loading with EF? - entity-framework

I have been using an AutoMapper and it seems that it gets me all the child entities (even if I don't specify them in "Include()" clause). Is there any way how to make lazy loading possible and get child properties only if I specify them.
Thank you,
Jakub

After mapping you will have mapped object without any references to source entity (which holds database context for lazy loading). Only property values are copied to destination entity. So you will not be able to do any lazy-loading without source entity.
Actually lazy loading works just fine for you - and it's occur during mapping process. You specified mappings for lazy-loaded properties of your entity, and mapper tries to get those values. That results in lazy-loading all navigation properties which you have configured for mapping. This is very inefficient. To disable lazy-loading during mapping you can ignore navigation properties in mapping configuration. E.g. if you have customer with lazy-loaded orders:
Mapper.CreateMap<Customer, CustomerDto>()
.ForMember(s => s.Orders, m => m.Ignore());
Or remove Orders property from your destination entity CustomerDto. If you need to have CustomerDto instance with orders inside, then best option is to do eager loading of orders, to avoid additional queries.

I think the best way is to define your mapping objects according to your need. In the mapping object define only the needed child entities.Let's say some DTOs like this mapping in to the Person entity in the domain.
class PersonDto
{
public string Name{get;set;}
public PersonLiteDto Parent{get; set;}
}
class PersonLiteDto
{
public string Name{get;set;}
//no navigation properties here..
}

Related

DbContext with dynamic DbSet

Is it possible to have a DbContext that has only one property of the generic type IDbSet and not a collection of concrete IDbSet e.g. DbSet.
More specifically, i want to create only one generic DbSet where the actual type will be determined dynamically e.g.
public new IDbSet<T> Set<T>() where T : class
{
return context.Set<T>();
}
I don't want to create multiple DbSets e.g.
DbSet<product> Products { get; set; }
...
Actually i tried to use that generic DbSet but there seems to be one problem. The DbContext doesn't create the corresponding tables in the database. So although i can work with the in-memory entity graph, when the time comes to store the entites into the DB an exception is thrown (Invalid object name 'dbo.Product'.)
Is there any way to force the EF to create tables that correspond to dynamicaly creates DbSets?
Yes you can do this.
modelBuilder.Configurations.Add
The DBSet entries will be derived.
If you plan to use POCOs and just build the model this way ok.
So you save Manual DBSet<> declaration...
But if you plan on being more Dynamic without POCOs...
Before you go down the this route, there are a number of things to consider.
Have you selected the right ORM ?
Do you plan on having a POCOs ?
Why is DbSet Products { get; set; } so bad ?
You get a lot of action for that 1 line of code.
What Data access approach you plan to use without types DBSets
Do you plan to use Linq to Entity statements?
do you plan on creating Expression trees for the Dynamic Data access necessary. Since the types arent known at compile time.
Do you plan to use the DB Model cache,?
How will the cache be managed, especially in Web. ASP environments.
There are most likely other issues i did think of off the top of my head.
Constructing the model yourself is a big task. The Linq access is compromised when compile time types/POCOs are NOT used and the model cache and performance become critical management tasks.
The practical side of this task is not to under estimate
Start here bContext.OnModelCreating
Typically, this method is called only once when the first instance of
a derived context is created. The model for that context is then
cached and is for all further instances of the context in the app
domain. This caching can be disabled by setting the ModelCaching
property on the given ModelBuidler, but this can seriously degrade
performance. More control over caching is provided through use of the
DbModelBuilder and DbContext classes directly.
The modelbuilder class
Good Luck

Query against Domain Classes should resolve against Entities

I am trying to build a generic repository that allows querying against domain classes.
My Repository interface looks like the following:
public interface IRepository<T>
{
T Get(int id);
IQueryable<T> Query();
void Add(T model);
void Remove(T model);
}
Given I have an UserEntity entity framework class and a User domain class, I want to query against the User. The UserEntity should not be exposed to other services, because it should be internal to the Entity Framework layer.
A query like userRepository.Query().Single(user => user.UserName == "Toni") should return a User domain class. However internally it should query against an IDbSet<UserEntity> returned from my entity framework. The Expression Tree (which contains the Single query operation) should be attached to a query against IDbSet<UserEntity>. After querying against IDbSet<UserEntity> I want to convert the UserEntity to a User domain class. Is this possible?
I have in mind to cerate an IQueryable implementation for my User class that internally queries against UserEntity.
public class MappedEntityQuery<TModel, TEntity> : IQueryable<TModel>
{
}
Code First requires the convention to have all IDbSet properties to access the tables to be in the DbContext
That is not true. You don't need to have any set declared in the context if you provide mapping to the entities in the model builder. In your case you should declare mapping through EntityTypeConfiguration<T> and ComplexTypeConfiguration<T> derived classes. You can create any DbSet instance of mapped entity type by calling Set<T>() on the context.
However for this project I am using a Database First approach, which also does not allow to load compose a DbContext using entities from different projects, because you have to specify the Database metadata in one single metadata file (which will be embedded).
That is true only partially. EDMX metadata must be in the single file embedded in the main project but entity classes do not have to if you use your own instead of auto-generated. So your proposed approach should work.
But if you really want to achieve modularity you should not use EDMX. If you decide to add or change any module in the future it would require changing central project as well but that can affect all other modules - it breaks the idea of modularity, doesn't it?

Private constructor on POCO entity preventing lazy loading

I have a POCO entity on which I have defined a custom constructor. I have also implemented the default constructor so that Entity Framework can successfully hydrate the object when I request a copy from the database.
This seems to work well but when I set the default constructor to private (to force my code to use the custom version) and request an entity from the database, I don't seem to be able to navigate over related entities as they are all null.
This seems to be a lazy loading problem so I could change my repository to eager load the related objects I need but am wondering if there is a better way to hide the default constructor from the client code whilst allowing Entity Framework to lazy load?
If you define private constructor you violate requirements for creating POCO proxy responsible for lazy loading:
A custom data class must have a public or protected constructor that
does not have parameters.
So the best option for you is using protected constructor or not using lazy loading.

EF 4.2 Code First and DDD Design Concerns

I have several concerns when trying to do DDD development with EF 4.2 (or EF 4.1) code first. I've done some extensive research but haven't come up with concrete answers for my specific concerns. Here are my concerns:
The domain cannot know about the persistence layer, or in other words the domain is completely separate from EF. However, to persist data to the database each entity must be attached to or added to the EF context. I know you are supposed to use factories to create instances of the aggregate roots so the factory could potentially register the created entity with the EF context. This appears to violate DDD rules since the factory is part of the domain and not part of the persistence layer. How should I go about creating and registering entities so that they correctly persist to the database when needed to?
Should an aggregate entity be the one to create it's child entities? What I mean is, if I have an Organization and that Organization has a collection of Employee entities, should Organization have a method such as CreateEmployee or AddEmployee? If not where does creating an Employee entity come in keeping in mind that the Organization aggregate root 'owns' every Employee entity.
When working with EF code first, the IDs (in the form of identity columns in the database) of each entity are automatically handled and should generally never be changed by user code. Since DDD states that the domain is separate from persistence ignorance it seems like exposing the IDs is an odd thing to do in the domain because this implies that the domain should handle assigning unique IDs to newly created entities. Should I be concerned about exposing the ID properties of entities?
I realize these are kind of open ended design questions, but I am trying to do my best to stick to DDD design patterns while using EF as my persistence layer.
Thanks in advance!
On 1: I'm not all that familiar with EF but using the code-first/convention based mapping approach, I'd assume it's not too hard to map POCOs with getters and setters (even keeping that "DbContext with DbSet properties" class in another project shouldn't be that hard). I would not consider the POCOs to be the Aggregate Root. Rather they represent "the state inside an aggregate you want to persist". An example below:
// This is what gets persisted
public class TrainStationState {
public Guid Id { get; set; }
public string FullName { get; set; }
public double Latitude { get; set; }
public double Longitude { get; set; }
// ... more state here
}
// This is what you work with
public class TrainStation : IExpose<TrainStationState> {
TrainStationState _state;
public TrainStation(TrainStationState state) {
_state = state;
//You can also copy into member variables
//the state that's required to make this
//object work (think memento pattern).
//Alternatively you could have a parameter-less
//constructor and an explicit method
//to restore/install state.
}
TrainStationState IExpose.GetState() {
return _state;
//Again, nothing stopping you from
//assembling this "state object"
//manually.
}
public void IncludeInRoute(TrainRoute route) {
route.AddStation(_state.Id, _state.Latitude, _state.Longitude);
}
}
Now, with regard to aggregate life-cycle, there are two main scenario's:
Creating a new aggregate: You could use a factory, factory method, builder, constructor, ... whatever fits your needs. When you need to persist the aggregate, query for its state and persist it (typically this code doesn't reside inside your domain and is pretty generic).
Retrieving an existing aggregate: You could use a repository, a dao, ... whatever fits your needs. It's important to understand that what you are retrieving from persistent storage is a state POCO, which you need to inject into a pristine aggregate (or use it to populate it's private members). This all happens behind the repository/DAO facade. Don't muddle your call-sites with this generic behavior.
On 2: Several things come to mind. Here's a list:
Aggregate Roots are consistency boundaries. What consistency requirements do you see between an Organization and an Employee?
Organization COULD act as a factory of Employee, without mutating the state of Organization.
"Ownership" is not what aggregates are about.
Aggregate Roots generally have methods that create entities within the aggregate. This makes sense because the roots are responsible for enforcing consistency within the aggregate.
On 3: Assign identifiers from the outside, get over it, move on. That does not imply exposing them, though (only in the state POCO).
The main problem with EF-DDD compatibility seems to be how to persist private properties. The solution proposed by Yves seems to be a workaround for the lack of EF power in some cases. For example, you can't really do DDD with Fluent API which requires the state properties to be public.
I've found only mapping with .edmx files allows you to leave Domain Entities pure. It doesn't enforce you to make things publc or add any EF-dependent attributes.
Entities should always be created by some aggregate root. See a great post of Udi Dahan: http://www.udidahan.com/2009/06/29/dont-create-aggregate-roots/
Always loading some aggregate and creating entities from there also solves a problem of attaching an entity to EF context. You don't need to attach anything manually in that case. It will get attached automatically because aggregate loaded from the repository is already attached and has a reference to a new entity. While repository interface belongs to the domain, repository implementation belongs to the infrastructure and is aware of EF, contexts, attaching etc.
I tend to treat autogenerated IDs as an implementation detail of the persistent store, that has to be considered by the domain entity but shouldn't be exposed. So I have a private ID property that is mapped to autogenerated column and some another, public ID which is meaningful for the Domain, like Identity Card ID or Passport Number for a Person class. If there is no such meaningful data then I use Guid type which has a great feature of creating (almost) unique identifiers without a need for database calls.
So in this pattern I use those Guid/MeaningfulID to load aggregates from a repository while autogenerated IDs are used internally by database to make a bit faster joins (Guid is not good for that).

how to load associated entities at server side for MS Entity frame work?

Suppose I have a couple of table:
person(personid, name, email)
employee(personid,cardno, departmentID) //personid,departmentID is foreign key
department(departmentID, departmentName)
employeePhone(personID, phoneID) //this is relationship table
phone(phoneID, phonenumer)
When EntityFramework generate entity class for employee, this class have members like:
public partial class employee{
int _personid;
string _cardno;
string _departmentName;
person _person;
department _department;
//......
}
by default, when this class is loaded, only data available for employee table column, not data for associated entities data loaded.
If I use Linq to get the data at client side, Include should be used for linq query.
My question is: I want to the associated entities data loaded at server side when the employee is instantiated at server side. So when I get the entity at client side, all data available already so that I can easy to bind it to UI.
How to implement this request?
Don't bind entity types to your UI. This couples the UI to the entity layer. Loading will be the least of your problems. With a coupled UI, you violate the single responsibility principle, require blacklists/whitelists to be maintained to have any form of security, break types which can't deal with circular references, you have poor performance because you load all fields from all related types, etc., etc., etc.
Instead, create a dedicated view model and project onto it:
var pm = (from e in Context.Employees
where e.Id == id
select new EmployeePresentation
{
EmployeeNumber = e.Number,
Name = e.Person.Name,
// etc.
}.First();
Because this is LINQ to Entities, the fields you reference in Person, etc., are automatically loaded, without requiring eager loading, lazy loading, or explicit Load(). But only those fields, not the entirety of Person, as with every other method.
Update, per comments
Using presentation models is also important for updates. It is not the case that I want a user to be able to update every field that they can see. Different presentation models for the same entity might have different validation/scaffolding rules since they're used at different points in data flow within the app. Also, the user should implicitly update fields they cannot see (e.g., timestamp).
Generically, my updates look like this (ASP.MVC Web app):
public ActionResult Update(EmployeePresentation model)
{
if (!ModelState.IsValid)
{
// User violated validation rule on presentation model.
return View(model);
}
Repository.Update(model.Id, delegate(Employee employee)
{
model.UpdateEmployee(employee);
});
return RedirectToAction("Index");
}
Note that there is no possibility of the user ever updating something they're not allowed to, in a typechecked, type-safe way, and that the model binding, the presentation model and the repository can all be extended for custom behavior.
What you are hoping for is Lazy loading of the dependent Entities. There is an article located at the link below that talks about this and at the bottom of the article it also give you an explanation of how to perform a lazy load should you still feel the need.
See "Configuring Lazy Loading in Entity Framework" in this article:
Entity Framework and Lazy Loading