c# - 在一个查询中加载关联实体

标签 c# dynamics-crm-2011

我有以下有效代码,但我相信它执行多次查找只是为了获取与我的自定义“项目”实体关联的“帐户”实体。

是否可以指定您想要填充哪些关联实体,而不必循环遍历初始结果集?

    public IList<new_project> GetAssociatedProjectsByPostcode(string postcode)
    {
        FilterExpression filter = new FilterExpression();
        filter.FilterOperator = LogicalOperator.And;
        filter.AddCondition(new ConditionExpression("new_project_zippostalcode", ConditionOperator.Equal, postcode));

        QueryExpression query = new QueryExpression();
        query.EntityName = new_project.EntityLogicalName;
        query.ColumnSet = new ColumnSet(true);
        query.Criteria = filter;

        OrganizationServiceCache serviceCache = new OrganizationServiceCache(MemoryCache.Default, base.CrmConnection);

        using (CachedOrganizationService service = new CachedOrganizationService(CrmConnection, serviceCache))
        using (XrmServiceContext xrmServiceContext = new XrmServiceContext(service))
        {
             //Run the query to return the project entities in a list
             IList<new_project> projects = service.RetrieveMultiple(query)
                                            .Entities
                                            .Select(item => item.ToEntity<new_project>())
                                            .ToList<new_project>();

             //Define the relationships we want populated
             Relationship accountRel = new Relationship("new_account_new_project");

             //We cannot call load property with tracking turned on 
             xrmServiceContext.MergeOption = MergeOption.NoTracking;

             //Loop through the original list and get our associations
             foreach (new_project np in projects)
                 xrmServiceContext.LoadProperty(np, accountRel);

             return projects;
        }            
    }

是否可以使用 ServiceContext 生成等效项?

Select Project.Name, Account.Name
From Project
Join Account ON Account.Id = Project.AccountId

编辑:

使用下面 James 描述的链接实体后,我现在得到了以下内容,它生成一个实体集合,其中包含在一个查询中填充的项目和帐户,但我无法将此平面数据集传输到分层对象结构中。

        public IList<new_project> GetAssociatedProjectsByPostcode(string postcode)
    {
        FilterExpression filter = new FilterExpression();
        filter.FilterOperator = LogicalOperator.And;
        filter.AddCondition(new ConditionExpression("new_project_zippostalcode", ConditionOperator.BeginsWith, PostcodeUtility.RegionFromPostcode(postcode)));

        QueryExpression query = new QueryExpression();
        query.EntityName = new_project.EntityLogicalName;
        query.ColumnSet = new ColumnSet(true);
        query.Criteria = filter;

        query.LinkEntities.Add(new LinkEntity(new_project.EntityLogicalName, Account.EntityLogicalName, "new_associatedaccountid", "accountid", JoinOperator.Inner));
        query.LinkEntities[0].Columns = new ColumnSet(true);
        query.LinkEntities[0].EntityAlias = Account.EntityLogicalName;

        OrganizationServiceCache serviceCache = new OrganizationServiceCache(MemoryCache.Default, base.CrmConnection);

        using (CachedOrganizationService service = new CachedOrganizationService(CrmConnection, serviceCache))
        using (XrmServiceContext xrmServiceContext = new XrmServiceContext(service))
        {
            EntityCollection ec = service.RetrieveMultiple(query);

            //*****************************************************************
            //The entity collection is now populated with the accounts but they
            //are just additional key value pairs
            //e.g. (String)((AliasedValue)ec[0]["account.name"]).Value;
            //*****************************************************************

            //Turn the entity collection into our class structure
            IList<new_project> projects = ec.Entities
                                           .Select(item => item.ToEntity<new_project>())
                                           .ToList<new_project>();
            return projects;
        }
    }

最佳答案

是的,这应该非常简单,您有几个选择。

  1. FetchXml,这是一种 xml 语法,与 tsql 的方法类似,它不具备所有功能,但您可以与 link-entity 进行连接,如下所示 MSDN .

  2. QueryExpression,有一个 LinkEntities 属性,可以像这样使用 MSDN

  3. 您可以发出 RetrieveRequest,填充 RelatedEntitiesQuery,如图 here


编辑

因此,实体集合看起来返回了我期望的结果(例如,这些帐户的帐户和值) - 我认为 typeof(ec[0]) 是实体?

所以这只是向早期边界的转换,这是错误的。

我没有太多使用 linq to crm,所以我开始猜测,但是从这个 example 来看.

您可能只需要:

  1. 在您的服务上启用ProxyTypes,显然这是完整早期绑定(bind)支持所必需的。
  2. 将实体转换为您的早期绑定(bind)类型。

例如(来自示例):

_serviceProxy.EnableProxyTypes();

Account retrievedAccount = (Account)_serviceProxy.Retrieve("account", _accountId, cols);

retrievedAccount.Address1_PostalCode = "98052";

Retrieve 仅返回一个实体(EntityCollection.Entities 的类型),并且转换似乎可以在这里工作。

关于c# - 在一个查询中加载关联实体,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12406025/

相关文章:

c# - 如何禁用 .NET/GDI+ 的子采样?

c# - 如何高效地创建和使用 builder 模式

dynamics-crm - 如何在事件 View 中添加 Dynamics CRM 自定义字段?

linq - LINQ 中 Where 语句中的错误

linq - 如何使用 LINQ 和连接检索 CRM Guid?

dynamics-crm-2011 - CRM 2011 中 UI 元素的正式名称和术语是什么?

c# - 如何管理用于XDocument格式化的 "NO-BREAK SPACE"?

C# 锁定在锁定 block 中重新分配的对象

c# - 在 VC++ 项目中使用 C# DLL 的内存泄漏

javascript - 通过 JavaScript 使用自定义页面打开 CRM 2011 表单后,子网格上的查找和链接不起作用