EF Query с условным включением, использующим соединения - PullRequest
0 голосов
/ 19 ноября 2011

Это продолжение к вопросу другого пользователя . У меня 5 столов

  • CompanyDetail
  • КомпанияКонтакты FK to CompanyDetail
  • КомпанияКонтактыБезопасность FK to CompanyContact
  • UserDetail
  • UserGroupMembership FK to UserDetail

Как мне вернуть все компании и включить контакты в один и тот же запрос? Я хотел бы включить компании, которые содержат ноль контактов.

Компании имеют связь «1 ко многим» с «Контактами», однако не каждому пользователю разрешено видеть каждый Контакт. Моя цель - получить список каждой компании независимо от количества контактов, но включить контактные данные.

Прямо сейчас у меня есть этот рабочий запрос:

 var userGroupsQueryable = _entities.UserGroupMembership
                          .Where(ug => ug.UserID == UserID)
                          .Select(a => a.GroupMembership);

var  contactsGroupsQueryable = _entities.CompanyContactsSecurity;//.Where(c => c.CompanyID == companyID);

/// OLD Query that shows permitted contacts
///  ... I want to "use this query inside "listOfCompany"
/// 
//var permittedContacts= from c in userGroupsQueryable
//join p in contactsGroupsQueryable on c equals p.GroupID
//select p;

Однако это неэффективно, когда мне нужно получить все контакты для всех компаний, поскольку я использую цикл For..Each, запрашиваю каждую компанию в отдельности и обновляю свою модель просмотра. Вопрос: Как мне ввести вышеуказанную переменную allowContacts выше и вставить его в этот запрос:

var listOfCompany = from company in _entities.CompanyDetail.Include("CompanyContacts").Include("CompanyContactsSecurity")
                where company.CompanyContacts.Any(

                // Insert Query here.... 
                 // b => b.CompanyContactsSecurity.Join(/*inner*/,/*OuterKey*/,/*innerKey*/,/*ResultSelector*/)

                )
                select company;

Моя попытка сделать это привела к:

var listOfCompany = from company in _entities.CompanyDetail.Include("CompanyContacts").Include("CompanyContactsSecurity")
                            where company.CompanyContacts.Any(


 // This is concept only... doesn't work...
 from grps in userGroupsQueryable
         join p in company.CompanyContactsSecurity on grps equals p.GroupID
        select p



)
select company;

Ответы [ 2 ]

1 голос
/ 19 ноября 2011

Возможно, что-то вроде этого.

var q = from company in _entities.CompanyDetail
        where 
        (from c in userGroupsQueryable
        join p in contactsGroupsQueryable on c equals p.GroupID
        where company.CompanyContacts.Any(cc => cc.pkCompanyContact == p.fkCompanyContact)
        select p
        ).Any()
        select new
        {
          Company = company,
          Contacts = company.CompanyContacts
        };
0 голосов
/ 19 ноября 2011

Следующий код запрашивает все компании и добавляет только те контакты, которые пользователь может видеть.Я не знаю, насколько это эффективно, или есть ли способ сделать это быстрее, но это работает.

 var userGroupsQueryable = _entities.UserGroupMembership.Where(ug => ug.UserID == UserID)
                                   .Select(a => a.GroupMembership);

 var  contactsGroupsQueryable = _entities.CompanyContactsSecurity;

 var listOfCompanies =
            from company in _entities.CompanyDetail
            select new
            {
                Company = company,
                Contacts = (from c in userGroupsQueryable
                            join p in contactsGroupsQueryable on c equals p.GroupID
                            where company.CompanyContacts.Any(cc => cc.CompanyID == p.CompanyID)
                            select p.CompanyContacts)
            };
...