使用 RIA 服务的 EF4 中的 Include() 域服务未加载!

发布于 2024-10-20 00:58:20 字数 3329 浏览 1 评论 0原文

我在使用 Include() 方法返回多个实体(急切加载)时遇到问题。我正在尝试使用 RIA 服务在 silverlight 应用程序中加载实体。数据模型由以下关系组成:

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

因此,一个事件可以有许多参与者,而一个参与者恰好是 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 个循环,用于查看事件参与者是否返回,但我从未收到从查询返回的任何参与者。 (在数据库中,我定义了 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;

DataModel.edmx 的 xml 表示形式中有一个注释。我认为这只是为了生成目的......但我也改变了它:

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

我已经在我的 SQL Server 2008 数据库中定义了关系。设计师选择了这些并在我的模型中创建了所有关系和导航属性。检查它们,它们看起来是有效的。如果我对包含语句中实体的拼写进行了粗略的检查,它会抛出一个错误,指出路径无效(或类似的效果)......所以我相信这些关系存在并且是有效的(并且我可以看到它们的定义在设计器代码等中)。

我已经删除了所有过滤,特别是在发出查询之前在查询上放置的附加连接。这是为了确保我不会遇到连接改变查询形状和破坏 Includes() 的问题。对人们来说似乎是一个大问题,我已经以这种方式消除了所有连接来隔离问题。它不是联接和包含的组合。

我已经重建了包含域服务和 RIA 服务 DLL 的 silverlight 项目,多次认为我的设置有误。我已经将 POCO 类生成器与 EF 一起使用,但后来发现您不能以与 POCO 相同的方式包含...所以我也放弃了它并返回到默认实体生成器。

我启动了 SQL Server 探查器,并从基本查询和包含 () 的查询中捕获了 SQL。包含的数据正在返回。我通过从探查器复制查询并直接发出来验证了这一点。查询的简化版本如下。这些关系是有效的,我可以看到所有相关数据都在那里(即参与者姓名、电话号码等)

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 为空。可悲的是。令人沮丧的是。痛苦地。 (我已经用完了“ly”)

我在互联网上搜索了解决方案,但没有发现任何人有同样的问题,而延迟加载设置、连接和包含的组合或不适当的导航无法解决特性。

我是不是错过了一些基本的事情?我是否遗漏了一个主要概念?我有一个来自旧雇主的另一个项目,他们执行相同的操作并且似乎有效。所以我确信这是可以做到的。就不是我的??

非常感谢任何帮助。我已经束手无策了。 提前致谢!

I am having trouble returning multiple entities (eager loading) using the Include() method. I am trying to load the entites in a silverlight application using RIA services. The Data Model consists of the following relationships:

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

So an Event can have many participants and a participant is exactly 1 user.

I can load the Event just fine, but I cannot get anything out of the child relationships specified by the Include() statement.

When I load up an Event, I am trying to pull in (using eager loading) all the EventParticipants and their associated user record. In my domain service I have the following:

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

    }

I then take the IQueryable that is returned and load it using my Domain Context on the client side like so:

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

(normally I would filter this but I simplified everything to get to the heart of the problem)

In my LoadOperationCompleted I have 2 loops that I use to see if the Event Participants are returned but I never receive any participants back from the query. (in the database, I have 242 Events defined...all of which have participants)

    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);
            }

        }

    }

I have also modified the above code (see below) to spin through the original domain context instead of the entities collection that is passed in through the load operation parameters to no avail. (events are there, children are not)

foreach (Event item in DomainContext.Events)

In my Data Model, there are three constructors (all generated) with varying parameters. In each I have disabled lazy loading like so:

this.ContextOptions.LazyLoadingEnabled = false;

There was an annotation in the xml representation of the DataModel.edmx. I think this is just for generation purposes...but I changed that too like so:

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

I have defined relationships in my SQL Server 2008 database. The designer picked these up and created all of the relationships and navigation properties in my model. Inspecting them, they appear valid. If I fat finger the spelling of the Entities in the include statement, it throws an error saying the path is not valid (or something to that effect)...so I believe the relationships exist and are functional (and I can see their definitions in the designer code and whatnot).

I have removed all the filtering and specifically the additional joins I have placed on the query before issuing it. This was to ensure I wasn't encountering the problem with joins changing the shape of the query and breaking the Includes(). Seems to be a big problem for people, I have eliminated all joins in this manner to isolate the problem. It is not a combination of joins and includes.

I have rebuilt my silverlight projects that house the domain service and RIA Services DLL a couple of times thinking I had some setting wrong. I have used the POCO class generator with EF but then read you can't include the same way with POCOs...so I scrapped that too and went back to the default entity generator.

I fired up SQL Server profiler and captured the SQL from a base query and one with Includes(). The data for the Includes ARE BEING RETURNED. I verified this by copying the query from profiler and issuing it directly. A simplified version of the query is as follows. The relationships are valid and I can see all the related data is there (i.e. participant names, phone numbers, etc)

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

However, when the entity is returned, the Event.EventParticipants EntityCollection is empty. Sadly. Frustratingly. Painfully. (I am out of "ly"s)

I have scoured the internet for solutions but haven't found anyone with the same problem that wasn't solved by the lazyloading setting, the combination of joins and includes or inappropriate navigation properties.

Have I just missed some basic thing? Is there a major concept that I am missing? I have another project from an old employer where they perform this same operation and it appears to work. So I am sure it can be done. Just not by me??

Any help is greatly appreciated. I am at my wits end. Thanks in advance!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

瞄了个咪的 2024-10-27 00:58:20

您是否尝试使用组合/包含属性将集合归因于模型?
这告诉 ria 服务也序列化实体集合,这里有几个链接可以帮助您走上正确的路径

WCF RIA 服务属性指南

WCF RIA 服务第 5 部分 - 元数据和共享类

RIA 服务中的组合支持


这是Tim 博客中的示例:

您需要手动编辑生成的 metadata.cs 文件(在 .txt 文件中保留更改列表)

[Include]
public EntityCollection<Album> Albums;

然后在域服务中执行以下操作:

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

Did you try attribute the collection on your model with the composition/include attribute?
this tells ria services to serialize the entitycollection as well, heres a couple of links to get you on the right path

A guide through WCF RIA Services attributes

WCF RIA Services Part 5 - Metadata and Shared Classes

Composition Support in RIA Services


This is the example from Tim's blog:

You need to manually edit the generated metadata.cs file (keep a list of changes in a .txt file)

[Include]
public EntityCollection<Album> Albums;

Then in the domain service do this:

public IQueryable<Artist> GetArtistsWithAlbums()
{
    return this.ObjectContext.Artists.Include("Albums");
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文