Reputation: 2078
Title might be confusing, so let me explain. Let's pretend I have a Dbo that looks like this:
public class EmployeeDbo
{
public int EmployeeId { get; set; }
public string FirstName{ get; set; }
public string LastName{ get; set; }
public string EmployeeData { get; set; }
public string EvenMoreEmployeeData{ get; set; }
}
And then somewhere in my data access layer I have this code:
// employeeId is some param that gets passed into this method
var query = _dbContext.Employees.Where(e => e.EmployeeId = employeeId);
// Now I want to further modify the query. I just want to load SOME values from the DB, instead of all of them
// The problem I have is that now this is trying to assign query, which is IQueryable<EmployeeDbo> to IQueryable<{string FirstName, string LastName}>
query = query.Select(e => new
{
e.FirstName,
e.LastName
});
// More code here that is expecting IQueryable<EmployeeDbo>
So, to summarize my question, how can I just populate SOME properties in a dbo with data from the DB? I suppose I could create a new Dbo with only the data I want as properties, but can I avoid doing that?
Upvotes: 0
Views: 503
Reputation: 34698
Using Select
is a Projection, it does not actually retrieve anything from the database, it just nominates what data you will want, and as such it should be moved to the end of your querying to avoid issues /w type.
If you just want to extract a sub-set of names from the query as it is at a particular point then you can use:
var results = query.Select(e => new
{
e.FirstName,
e.LastName
}).ToList();
ToList()
is actually what executes the query at that point and returns the results into the "results" variable, leaving the "query" variable to be further refined and ultimately consumed.
Otherwise, if you're only going to want to return these details for a view, you need to move the Select
towards the end of the search expression chain. The only thing after a Select
will typically be ToList
and pagination, (Skip
/Take
) or Single
/First
etc.
Upvotes: 1
Reputation: 31
Entity Framework keeps an exclusive control on the queries it generates. The DbSets have this mapping defined for the Entities in the corresponding EDMX file in XML notation.
<EntityType Name="Table1">
<Key>
<PropertyRef Name="Id" />
</Key>
<Property Name="Id" Type="int" StoreGeneratedPattern="Identity" Nullable="false" />
<Property Name="Column01" Type="int" />
<Property Name="Column02" Type="int" Nullable="false" />
<Property Name="Column03" Type="varchar" MaxLength="30" />
<Property Name="Column04" Type="varchar" MaxLength="10" />
</EntityType>
New instances created "using query.Select(e => new" and eliminating some fields from the output will simply ignore these entity fields. These fields will still be pulled from the database.
As far as I know there is currently no way to "load SOME values from the DB" using EF context. I would not recommend modifying Entity Classes or EDMX manually as it may have some unforeseen issues.
You can examine the queries Entity Framework generates in Visual Studio output window using the below before running the EF query in Visual Studio.
context.Database.Log = s => System.Diagnostics.Debug.WriteLine(s);
If you want to limit the data load from Entity Framework then consider using stored procedures instead or use other Micro ORMs such as Dapper for a more fine grained control on your data.
Upvotes: 0