Включить() в EF4 с помощью службы домена RIA Services не загружается!

96
6

У меня возникли проблемы с возвратом нескольких объектов (загружаемая загрузка) с помощью метода Include(). Я пытаюсь загрузить entites в приложении silverlight с использованием служб RIA. Модель данных состоит из следующих соотношений:


Events.ID = EventParticipants.EventsID
EventParticipants.ParticipantUserID = Users.ID


Таким образом, у Event может быть много участников, а участник - ровно 1 пользователь.


Я могу загрузить событие просто отлично, но я не могу получить ничего из дочерних отношений, указанных в инструкции Include().


Когда я загружаю Событие, я пытаюсь задействовать (используя загрузку) всех участников EventParticipants и связанных с ними записей пользователей. В моей службе домена у меня есть следующее:


    public IQueryable<Event> GetEvents()
{
return this.ObjectContext.Events
.Include("EventParticipants")
.Include("EventParticipants.User");

}


Затем я беру возвращаемый IQueryable и загружаю его с помощью моего контекста домена на стороне клиента следующим образом:


DomainContext.Load(DomainContext.GetEventsQuery(), LoadOperationCompleted, true);

(обычно я бы отфильтровал это, но я упростил все, чтобы понять суть проблемы)


В моем LoadOperationCompleted у меня есть 2 цикла, которые я использую, чтобы проверить, возвращены ли участники Event, но я никогда не получаю от участников ответа. (в базе данных у меня определено 242 события... все из которых имеют участников)


    private void LoadOperationCompleted(LoadOperation lo)
{

if (lo.Error != null)
{
Debugger.Break();
lo.MarkErrorAsHandled();
}

foreach (Event item in lo.Entities)
{

foreach (var particpant in item.EventParticipants)
{
Debug.WriteLine("{0} {1}", particpant.User.First, particpant.User.Last);
}

}

}


Я также модифицировал приведенный выше код (см. ниже), чтобы прокручивать исходный контекст домена вместо коллекции сущностей, которая передается через параметры операции загрузки безрезультатно. (события есть, детей нет)


foreach (Event item in DomainContext.Events)

В моей модели данных есть три конструктора (все сгенерированные) с различными параметрами. В каждом я отключил ленивую загрузку так:


this.ContextOptions.LazyLoadingEnabled = false;

В XML-представлении DataModel.edmx появилась аннотация. Я думаю, что это только для целей генерации... но я тоже изменил это:


<EntityContainer Name="MyCrazyEntities" annotation:LazyLoadingEnabled="false">

Я определил отношения в моей базе данных SQL Server 2008. Дизайнер подобрал их и создал все свои отношения и свойства навигации в моей модели. Проверяя их, они выглядят действительными. Если бы я толкнул написание сущностей в заявлении include, это порождает ошибку, указывающую, что путь недействителен (или что-то в этом роде)... поэтому я считаю, что отношения существуют и являются функциональными (и я могу видеть их определения в коде дизайнера и еще что-то).


Я удалил всю фильтрацию и, в частности, дополнительные соединения, которые я поместил в запрос перед его выпуском. Это должно было гарантировать, что я не столкнулся с проблемой, когда соединения меняют форму запроса и разбивают Includes(). Кажется, это большая проблема для людей, поэтому я устранил все объединения таким образом, чтобы изолировать проблему. Это не комбинация объединений и включает.


Я перестроил свои проекты в Silverlight, которые несколько раз размещали службу домена и RIA Services DLL, думая, что у меня некорректная настройка. Я использовал генератор класса POCO с EF, но затем прочитал, что вы не можете включить тот же путь с POCOs... поэтому я тоже отказался от него и вернулся к генератору сущностей по умолчанию.


Я активировал профилировщик SQL Server и захватил SQL из базового запроса, а другой - с Includes(). Данные для Includes ВОЗВРАЩАЮТСЯ. Я проверил это, скопировав запрос из профилировщика и выпустив его напрямую. Упрощенная версия запроса выглядит следующим образом. Эти отношения действительны, и я вижу, что все связанные с ними данные есть (например, имена участников, номера телефонов и т.д.)


SELECT 
'trimmed fields for brevity>'
FROM ( SELECT
'trimmed fields for brevity>'
CASE WHEN ([Join1].[ID1] IS NULL) THEN CAST(NULL AS int) ELSE 1 END AS [C1]
FROM [dbo].[Events] AS [Extent1]
LEFT OUTER JOIN (SELECT 'trimmed fields for brevity>'
FROM [dbo].[EventParticipants] AS [Extent2]
INNER JOIN [dbo].[Users] AS [Extent3] ON [Extent2].[ParticipantUsersID] = [Extent3].[ID] ) AS [Join1] ON [Extent1].[ID] = [Join1].[EventsID]
) AS [Project1]
ORDER BY [Project1].[ID] ASC, [Project1].[C1] ASC

Однако, когда объект возвращается, Event.EventParticipants EntityCollection пуст. К сожалению. Разочаровывающе. Больно. (Я из "ли" )


Я просмотрел интернет для решений, но не нашел никого с той же проблемой, которая не была решена параметром lazyloading, комбинацией соединений и включает или неприемлемые свойства навигации.


Я просто пропустил какую-то основную вещь? Есть ли принципиальная концепция, которую мне не хватает? У меня есть еще один проект от старого работодателя, где они выполняют эту же операцию и, похоже, работают. Поэтому я уверен, что это можно сделать. Просто не я?


Любая помощь приветствуется. Я нахожусь на своем пути. Спасибо заранее!

спросил(а) 2021-01-19T17:42:19+03:00 2 месяца, 3 недели назад
1
Решение
87

Попробовали ли атрибут коллекции на вашей модели с атрибутом состава /include?
 это говорит службам ria для сериализации сущности, а также несколько ссылок, которые помогут вам найти правильный путь.


Руководство по атрибутам служб WCF RIA


Услуги WCF RIA Часть 5 - Метаданные и общие классы


Поддержка композиции в службах RIA

Это пример из блога Тима:


Вам нужно вручную отредактировать сгенерированный файл metadata.cs (сохранить список изменений в TXT файле)


[Include]
public EntityCollection<Album> Albums;

Затем в службе домена выполните следующее:


public IQueryable<Artist> GetArtistsWithAlbums()
{
return this.ObjectContext.Artists.Include("Albums");
}

ответил(а) 2021-01-19T17:42:19+03:00 2 месяца, 3 недели назад
Ваш ответ
Введите минимум 50 символов
Чтобы , пожалуйста,
Выберите тему жалобы:

Другая проблема