Reputation: 81
You can probably see the result I want to get. It's easy using loop, but I can't understand how to achieve such result using LINQ extension methods
I have two contexts that target one DB. ApplicationUser is authentication class, and profileDTO profile info that I get from same DB.
ProfileDTO properties: string Id, string FirstName, string LastName
Both tables share same ID but are not connected neither through navigation properties nor any references in the DB.
IEnumerable<ViewModels.User.IndexViewModel> model;
IEnumerable<Models.ApplicationUser> users;
var profilesDtos = _profileService.GetAll();
using (var context = new Models.ApplicationDbContext())
{
users = context.Users.ToList();
}
model = users.Select(user =>
new ViewModels.User.IndexViewModel
{
Id = user.Id,
Email = user.Email,
PhoneNumber = user.PhoneNumber,
LockedOutTill = user.LockoutEndDateUtc ?? default(DateTime),
Roles = UserManager.GetRoles(user.Id)
});
foreach (var user in model)
{
var userProfile = profilesDtos.FirstOrDefault(o => o.Id == user.Id);
if (userProfile != null)
{
user.FirstName = userProfile.FirstName;
user.LastName = userProfile.LastName;
}
};
I want to get all users but with Names set only in those who have profiles.
Upvotes: 1
Views: 609
Reputation: 2607
You can use left join in Linq, like below -
IEnumerable<ViewModels.User.IndexViewModel> model;
IEnumerable<Models.ApplicationUser> users;
var profilesDtos = _profileService.GetAll();
using (var context = new Models.ApplicationDbContext())
{
users = context.Users.ToList();
}
model = (from u in users
join p in profilesDtos on u.Id equals p.Id into tempTbl
from up in tempTbl.DefaultIfEmpty()
select new ViewModels.User.IndexViewModel
{
Id = u.Id,
Email = u.Email,
PhoneNumber = u.PhoneNumber,
LockedOutTill = u.LockoutEndDateUtc ?? default(DateTime),
Roles = UserManager.GetRoles(u.Id),
FirstName = up!= null? up.FirstName : string.Empty;
LastName = up!= null? up.LastName : string.Empty;
}).ToList();
Upvotes: 1
Reputation: 1
As a solution, you can just join them.
Plus DefaultIfEmpty statement.
Upvotes: 0
Reputation: 6260
First of all I would suggest to update your context to setup such property. If you can't do this use JOIN
:
var result =
from user in context.Users
join profile in userProfiles on user.ID equals profile.ID
select new ViewModels.User.IndexViewModel {
Id = user.Id,
FirstName = profile.FirstName,
...
}
Upvotes: 0