Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Loading all the children entities with entity framework

Tags:

I have a data model like this

Data Model

I would like to load all the related entities from a Reconciliation into a Reconciliation object.

For now the only way I could find to load all the related entites to a single Recon is in multiple Lists. But I want to load every related entities in a Reconciliation object. If possible in an elegant way.

Reconciliation recon = db.Reconciliations   .Where(r => r.ReconNum == 382485).First();  List<ReconciliationDetail> reconDetails = recon.ReconciliationDetails.ToList(); List<JrnlEntryDetail> jrnlDetails = reconDetails.Select(r => r.JrnlEntryDetail).ToList(); List<JrnlEntry> jrnl = jrnlDetails.Select(j => j.JrnlEntry).ToList();  List<ARInvoice> invoices = jrnl.SelectMany(j => j.ARInvoices).ToList(); List<ARInvoiceDetail> invoicesDetail = invoices   .SelectMany(i => i.ARInvoiceDetails).ToList();  List<ARCredMemo> credmemos = jrnl.SelectMany(j => j.ARCredMemoes).ToList(); List<ARCredMemoDetail> credmemosDetail = credmemos   .SelectMany(c => c.ARCredMemoDetails).ToList();  List<IncomingPay> incomingPays = jrnl.SelectMany(j => j.IncomingPays).ToList(); List<IncomingPayDetail> incomingPaysDetail = incomingPays   .SelectMany(i => i.IncomingPayDetails).ToList();  // ... and so on for outgoing pays, AP Invoices AP Cred Memo ...etc 

I have also tried to load it with Include and Select but I get this exception :

The Include path expression must refer to a navigation property defined on the type. Use dotted paths for reference navigation properties and the Select operator for collection navigation properties.

And I don't get how I could load every childs of JrnlEntry using Include and Select

Reconciliation recon = db.Reconciliations   .Where(r => r.ReconNum == 382485)   .Include(r => r.ReconciliationDetails     .Select(d => d.JrnlEntryDetail)     .Select(jd => jd.JrnlEntry)     .SelectMany(j => j.ARInvoices).SelectMany(i => i.ARInvoiceDetails)) 

Edit

Managed to do it this way too but it's not very beautiful :

Reconciliation recon = db.Reconciliations .Where(r => r.ReconNum == 382485)   .Include(r => r.ReconciliationDetails.Select(rd => rd.JrnlEntryDetail)     .Select(jd => jd.JrnlEntry).Select(j => j.ARInvoices.Select(i => i.ARInvoiceDetails)))   .Include(r => r.ReconciliationDetails.Select(rd => rd.JrnlEntryDetail)     .Select(jd => jd.JrnlEntry).Select(j => j.ARCredMemoes.Select(c => c.ARCredMemoDetails)))   .Include(r => r.ReconciliationDetails.Select(rd => rd.JrnlEntryDetail)     .Select(jd => jd.JrnlEntry).Select(j => j.IncomingPays.Select(i => i.IncomingPayDetails)))   .Include(r => r.ReconciliationDetails.Select(rd => rd.JrnlEntryDetail)     .Select(jd => jd.JrnlEntry).Select(j => j.OutgoingPays.Select(o => o.OutgoingPayDetails)))   .Include(r => r.ReconciliationDetails.Select(rd => rd.JrnlEntryDetail)     .Select(jd => jd.JrnlEntry).Select(j => j.APInvoices.Select(o => o.APInvoiceDetails)))   .Include(r => r.ReconciliationDetails.Select(rd => rd.JrnlEntryDetail)     .Select(jd => jd.JrnlEntry).Select(j => j.APCredMemoes.Select(o => o.APCredMemoDetails)))   .Include(r => r.ReconciliationDetails.Select(rd => rd.JrnlEntryDetail)     .Select(jd => jd.JrnlEntry).Select(j => j.JrnlEntryDetails)) 
like image 936
Arno 2501 Avatar asked Nov 08 '13 13:11

Arno 2501


People also ask

What are the way of loading data in Entity Framework?

Entity Framework supports three ways to load related data - eager loading, lazy loading and explicit loading.

What is lazy loading and eager loading in Entity Framework?

Lazy loading in Entity Framework is the default phenomenon that happens for loading and accessing the related entities. However, eager loading is referred to the practice of force-loading all these relations.

How do I enable eager loading in Entity Framework?

Eager loading is the process whereby a query for one type of entity also loads related entities as part of the query. Eager loading is achieved by the use of the Include method. It means that requesting related data be returned along with query results from the database.

How do I load related data in EF core?

Entity Framework Core allows you to use the navigation properties in your model to load related entities. There are three common O/RM patterns used to load related data. Eager loading means that the related data is loaded from the database as part of the initial query.


1 Answers

There are two ways to perform Eager Loading in Entity Framework:

  • ObjectQuery.Include Method
  • Explicit loading using either DbEntityEntry.Collection Method or DbEntityEntry.Reference Method along with their respective Load methods

There are also manners to write Raw SQL Queries against database:

  • DbSet.SqlQuery Method deals with entities
  • Database.SqlQuery Method deals with arbitrary types
  • Database.ExecuteSqlCommand Method for arbitrary DDL/DML

For the case, when you're attempting to load nearly entire database, it would be good idea to execute dedicated store procedure against it.

like image 149
Ryszard Dżegan Avatar answered Nov 15 '22 10:11

Ryszard Dżegan