首页 > 其他分享 >Dynamics CRM 365 使用FetchXml 查询数据(Query data using FetchXml )

Dynamics CRM 365 使用FetchXml 查询数据(Query data using FetchXml )

时间:2024-06-17 09:56:18浏览次数:19  
标签:entity fetchXml FetchXml link 使用 using 查询 data

前言

FetchXml 是一种基于 XML 的专有查询语言,用于从 Dataverse 检索数据。

添加引用

  1. Microsoft.CrmSdk.CoreAssemblies
  2. System.Configuration

检索数据(Retrieve data)

RetrieveMultiple

using Microsoft.Xrm.Sdk.Query;
using Microsoft.Xrm.Sdk;
using Microsoft.Xrm.Tooling.Connector;
using System;
using System.Configuration;
using System.Linq;

namespace FetchXml
{
    internal class Program
    {
        static void Main(string[] args)
        {
            CrmServiceClient service = new CrmServiceClient(ConfigurationManager.ConnectionStrings["CRMConnString"].ConnectionString);
            string fetchXml = @"<fetch top='5'><entity name='account'><attribute name='name' /></entity></fetch>";
            EntityCollection entityCollection = RetrieveMultipleExample(service, fetchXml);
            entityCollection.Entities.ToList().ForEach(e =>
            {
                Console.WriteLine($"Name:{e.GetAttributeValue<string>("name")}");
            });
            Console.WriteLine();
            Console.ReadKey();
        }

        static EntityCollection RetrieveMultipleExample(IOrganizationService service, string fetchXml)
        {
            return service.RetrieveMultiple(new FetchExpression(fetchXml));
        }
    }
}

RetrieveMultipleRequest

using Microsoft.Xrm.Sdk.Query;
using Microsoft.Xrm.Sdk;
using Microsoft.Xrm.Tooling.Connector;
using System;
using System.Configuration;
using System.Linq;
using Microsoft.Xrm.Sdk.Messages;

namespace FetchXml
{
    internal class Program
    {
        static void Main(string[] args)
        {
            CrmServiceClient service = new CrmServiceClient(ConfigurationManager.ConnectionStrings["CRMConnString"].ConnectionString);
            string fetchXml = @"<fetch top='5'><entity name='account'><attribute name='name' /></entity></fetch>";
            EntityCollection entityCollection1 = RetrieveMultipleRequestExample(service, fetchXml);
            entityCollection1.Entities.ToList().ForEach(e =>
            {
                Console.WriteLine($"AccountName:{e.GetAttributeValue<string>("name")}");
            });
            Console.WriteLine();
            Console.ReadKey();
        }
        static EntityCollection RetrieveMultipleRequestExample(IOrganizationService service, string fetchXml)
        {
            var request = new RetrieveMultipleRequest()
            {
                Query = new FetchExpression(fetchXml)
            };

            var response = (RetrieveMultipleResponse)service.Execute(request);

            return response.EntityCollection;
        }
    }
}

选择列(Select columns)

attribute

当使用FetchXml查询数据时,通过使用entity元素选择表来启动查询。

使用 attribute 选择要随查询返回的列。例如:

<fetch top='5'>
  <entity name='account'>
    <attribute name='accountclassificationcode' />
    <attribute name='createdby' />
    <attribute name='createdon' />
    <attribute name='name' />
  </entity>
</fetch>
string fetchXml = @"<fetch top='5'>
            <entity name='account'>
                <attribute name='accountclassificationcode' />
                <attribute name='createdby' />
                <attribute name='createdon' />
                <attribute name='name' />
            </entity>
            </fetch>";
FetchExpression fetchExpression = new FetchExpression(fetchXml);
//Retrieve the data
EntityCollection entityCollection = service.RetrieveMultiple(query: fetchExpression);

此查询返回了Account表中前5行的accountclassificationcode,createdby,createdonname列。此处使用了top限制了返回结果的大小。如果没有top限制,会默认返回前5000行数据

一般情况是不建议返回表中的所有列,返回所有列将使应用程序运行速度变慢,并可能导致超时错误。应该需要按照需要返回自己所需要的列。

all-attributes

使用all-attributes元素可以返回表中所有列。

若在FetchXml中未指定列,也能返回所有列,但是并不建议这样做。

string fetchXml = @"<fetch top='5'>
           <entity name='account'>
                <all-attributes/>
           </entity>
           </fetch>";
//string fetchXml = @"<fetch top='5'>
        //<entity name='account'>
        //</entity>
        //</fetch>";
FetchExpression fetchExpression = new FetchExpression(fetchXml);
//Retrieve the data
EntityCollection entityCollection = service.RetrieveMultiple(query: fetchExpression);

column aliases

使用 attribute alias属性为返回的结果指定唯一的列名。

返回的每一列都必须具有唯一的名称。默认情况下,为查询的表返回的列名是列LogicalName值。每个表的所有列逻辑名称都是唯一的,因此该集合中不能有任何重复的名称。

使用 link-entity 元素联接表时,默认列名遵循以下命名约定:{Linked table LogicalName}.{Column LogicalName}。这样可以防止任何重复的列名。您可以使用唯一的别名来覆盖此项。您还可以为表示联接表设置一个值。

string fetchXml = @"<fetch top='3'>
                    <entity name='account'>
                    <attribute name='accountclassificationcode' alias='code' />
                    <attribute name='createdby' alias='whocreated' />
                    <attribute name='createdon' alias='whencreated' />
                    <attribute name='name' alias='companyname' />
                    </entity>
                    </fetch>";
FetchExpression fetchExpression = new FetchExpression(fetchXml);
//Retrieve the data
EntityCollection entityCollection = service.RetrieveMultiple(query: fetchExpression);
foreach (var entity in entityCollection.Entities)
{
    var code = ((OptionSetValue)entity.GetAttributeValue<AliasedValue>("code").Value).Value;
    var whocreated = ((EntityReference)entity.GetAttributeValue<AliasedValue>("whocreated").Value).Name;
    var whencreated = entity.GetAttributeValue<AliasedValue>("whencreated").Value;
    var companyname = entity.GetAttributeValue<AliasedValue>("companyname").Value;
    Console.WriteLine($"code:{code},whocreated:{whocreated},whencreated:{whencreated},companyname:{companyname}");
}

联接表(Join tables)

Many-to-one relationship

此查询根据客户记录中的 PrimaryContactId 查找列从客户和联系人表返回数据:

<fetch>
  <entity name='account'>
    <attribute name='name' />
    <link-entity name='contact' from='contactid' to='primarycontactid' link-type='inner' alias='contact'>
      <attribute name='fullname' />
    </link-entity>
  </entity>
</fetch>

One-to-many relationship

此查询基于联系人account_primary_contact一对多关系从联系人和客户表中返回数据。

<fetch>
  <entity name='contact'>
    <attribute name='fullname' />
    <link-entity name='account' from='primarycontactid' to='contactid' alias='account'>
      <attribute name='name' />
    </link-entity>
  </entity>
</fetch>

Many-to-many relationship

此查询使用teammembership_association多对多关系从 SystemUser 和 Team 表返回数据。

<fetch>
  <entity name='systemuser'>
    <attribute name='fullname' />
    <link-entity name='teammembership' from='systemuserid' to='systemuserid' >
      <link-entity name='team' from='teamid' to='teamid' link-type='inner' alias='team'>
        <attribute name='name' />
      </link-entity>
    </link-entity>
  </entity>
</fetch>

No relationship

可以使用不属于已定义关系的列来指定from和to属性。

例如,此查询查找记录对,其中客户记录的“名称”列与联系人记录的“完整名称”列匹配,而不管它们是否在任何查找列中相互引用。

<fetch>
   <entity name='account'>
     <attribute name='name' />
     <link-entity name='contact' from='fullname' to='name' link-type='inner' alias='contact'>
       <attribute name='fullname' />
     </link-entity>
   </entity>
 </fetch>

重要的是,在from和to属性中指定的列是相同的类型,即使它们不涉及关系。使用不同类型的列将需要类型转换,这可能会对性能产生影响,并且可能会对某些列值失败。

以下列类型不能在from和to属性中使用:

某些列可以在from和to属性中使用,但可能会导致较差的性能:

  • 多行文本类型的列
  • 最大长度大于850的单行文本类型的列
  • 公式列
  • 计算列
  • 逻辑列

Attributes

名字 必填? 描述
name 相关表的逻辑名称。
to 父元素中要与from属性中指定的相关表列匹配的列的逻辑名称。
from 与to属性中指定的列匹配的相关表中的列的逻辑名称。
alias 表示相关表的名称。如果不设置别名,将为您生成一个别名,以确保所有列都具有唯一的名称,但您将无法使用该别名来引用fetch XML的其他部分中的链接实体。自动生成的别名使用模式{LogicalName}+{N},其中N是从1开始的获取XML中链接实体的序列号。
link-type 链接使用的类型。默认行为是 inner.
intersect 指示链接实体用于联接表而不返回任何列,通常用于多对多关系。此属性的存在不会更改查询的执行。在联接表时,可以将此属性添加到链接实体中,但不包含任何属性元素以表明这是有意的。

使用link-type对返回的记录应用筛选器。下表介绍了有效的link-type值:

Name Description
inner 默认,将结果限制为两个表中具有匹配值的行。
outer 包括父元素中没有匹配值的结果。
any filter element中使用此功能。将结果限制为在链接实体中具有任何匹配行的父行。
not any filter element中使用此功能。将结果限制为链接实体中没有匹配行的父行。
all filter element中使用此功能。将结果限制为父行,其中链接实体中存在与from列值匹配的行,但这些匹配行都不满足为此链接实体定义的其他筛选器。您需要反转额外的过滤器,以找到每个匹配链接实体行都满足某些额外条件的父行。
not all filter element中使用此功能。将结果限制为链接实体中具有任何匹配行的父行。无论名称如何,此链接类型都等效于任何链接类型。
exists inner的一种变形,可以提升性能。在where子句中使用EXISTS条件。当结果中不需要父行的多个副本时,请使用此选项。
in inner的一种变形,可以提升性能。在where子句中使用IN条件。当结果中不需要父行的多个副本时,请使用此选项。
matchfirstrowusingcrossapply inner的一种变形,可以提升性能。当链接实体中只有一个匹配行的示例就足够了,并且不需要结果中父行的多个副本时,请使用此类型。

exists

FetchXml

<fetch>
   <entity name='contact'>
      <attribute name='fullname' />
      <link-entity name='account' from='primarycontactid' to='contactid' link-type='exists'>
         <filter type='and'>
            <condition attribute='statecode' operator='eq' value='1' />
         </filter>
      </link-entity>
   </entity>
</fetch>

SQL

select 
    "contact0".fullname as "fullname" 
from Contact as "contact0" 
where exists (
    select "account1".primarycontactid
    from Account as "account1"
    where "account1".statecode = 1
        and "contact0".contactid = "account1".primarycontactid)

in

FetchXml

<fetch>
   <entity name='contact'>
      <attribute name='fullname' />
      <link-entity name='account' from='primarycontactid' to='contactid' link-type='in'>
         <filter type='and'>
            <condition attribute='statecode' operator='eq' value='1' />
         </filter>
      </link-entity>
   </entity>
</fetch>

SQL

select 
    "contact0".fullname as "fullname" 
from Contact as "contact0" 
where "contact0".contactid in (
    select "account1".primarycontactid
    from Account as "account1"
    where "account1".statecode = 1)

matchfirstrowusingcrossapply

FetchXml

<fetch>
   <entity name='contact'>
      <attribute name='fullname' />
      <link-entity name='account' from='primarycontactid'  to='contactid'  link-type='matchfirstrowusingcrossapply'>
         <attribute name='accountid' />
         <attribute name='name' />
      </link-entity>
   </entity>
</fetch>

SQL

select 
    "contact0".fullname as "fullname",
    "account1".accountid as "accountid",
    "account1".name as "name" 
from Contact as "contact0"
cross apply (
    select top 1
        "account1".accountid as "accountid",
        "account1".name as "name"
    from Account as "account1"
    where "contact0".contactid = "account1".primarycontactid
  ) "account1"

局限性

一个查询最多可以添加15个link-entity元素。每个链接实体都会向查询添加一个JOIN,并增加执行查询的时间。此限制是为了保护性能。如果向查询添加了超过15个link-entity元素,则会出现以下错误:

Code: 0x8004430D
Number: -2147204339
Message: Number of link entities in query exceeded maximum limit.

对行进行排序 (Order rows)

升序排列

若要指定表中行的排序顺序,请使用 entity 或 link-entity 元素中的 order元素。默认排序顺序为升序。

下面的查询按createdonnameaccountnumber的值升序返回客户记录。

<fetch>
  <entity name='account'>
    <attribute name='name' />
    <attribute name='accountnumber' />
    <attribute name='createdon' />
    <order attribute='createdon' />
    <order attribute='name' />
    <order attribute='accountnumber' />
  </entity>
</fetch>

元素的顺序决定了如何应用排序。要使用accountnumber应用排序,请将该元素移动到第一个位置。

降序排列

如果要使用降序排列,请将descending属性设置为true。下面的示例返回客户记录,顶部是最近创建的记录。

<fetch>
  <entity name='account'>
    <attribute name='name' />
    <attribute name='createdon' />
    <order attribute='createdon' descending='true' />
  </entity>
</fetch>

Dataverse总是将link-entity指定的属性排在实体元素的属性之后。

下面的示例显示了link-entity属性和entity属性的常规排序模式。

<fetch>
  <entity name='account'>
    <attribute name='name' />
    <attribute name='accountnumber' />
    <attribute name='createdon' />
    <link-entity name='account'
      from='accountid'
      to='parentaccountid'
      link-type='inner'
      alias='parentaccount'>
      <attribute name='name'
        alias='parentaccount' />
        <!-- The link-entity parentaccount name -->
      <order attribute='name' />
    </link-entity>
    <!-- The entity account name -->
    <order attribute='name' />
  </entity>
</fetch>

在这种情况下,结果使用以下属性排序:

  • First => account.name
  • Last => parentaccountname.name

要确保首先应用link-entity顺序,请将order元素从link-entity元素移动到另一个order元素上方的entity元素,并使用order元素上的entityname属性来引用link-entity alias值。

<fetch>
  <entity name='account'>
    <attribute name='name' />
    <attribute name='accountnumber' />
    <attribute name='createdon' />
    <link-entity name='account'
      from='accountid'
      to='parentaccountid'
      link-type='inner'
      alias='parentaccount'>
      <attribute name='name'
        alias='parentaccount' />
    </link-entity>
    <!-- The link-entity parentaccount name -->
    <order entityname='parentaccount'
      attribute='name' />
      <!-- The entity account name -->
    <order attribute='name' />
  </entity>
</fetch>

现在,使用以下属性对结果进行排序:

  • First => parentaccount.name
  • Last => account.name

过滤行 (Filter rows)

filter

若要对要返回的数据行设置条件,请在实体、链接实体或其他元素中使用 filter 元素。

要设置条件,请向filter添加一个或多个 condition元素。包含filter type确定是否必须满足所有(and)或任何(or)条件。默认值是and。通过嵌套筛选元素,您可以创建复杂的filter条件,将使用andor评估的条件组合在一起。

filter type='and'

例如,下面的查询返回address1_city等于'Redmond'的帐户记录。它使用eq操作符。

<fetch>
   <entity name='account'>
      <attribute name='name' />
      <filter type='and'>
         <condition attribute='address1_city'
            operator='eq'
            value='Redmond' />
      </filter>
   </entity>
</fetch>

filter type='or'

这个查询返回address1_city等于'Redmond'、'Seattle'或'Bellevue'的帐户记录。它使用和三个条件元素,每个元素都使用eq操作符。

<fetch>
   <entity name='account'>
      <attribute name='name' />
      <attribute name='address1_city' />
      <filter type='or'>
         <condition attribute='address1_city'
            operator='eq'
            value='Redmond' />
         <condition attribute='address1_city'
            operator='eq'
            value='Seattle' />
         <condition attribute='address1_city'
            operator='eq'
            value='Bellevue' />
      </filter>
   </entity>
</fetch>

对同一行中的列值进行筛选

可以使用valueof属性创建筛选器,比较同一行中各列的值。例如,如果你想查找任何firstname列值与lastname列值匹配的联系人记录,你可以使用这个查询:

<fetch>
   <entity name='contact' >
      <attribute name='firstname' />
      <filter>
         <condition attribute='firstname'
            operator='eq'
            valueof='lastname' />
      </filter>
   </entity>
</fetch>

局限性

在FetchXml查询中包含的条件和链接实体元素总数不能超过500个。否则,你会看到这个错误:

Name: TooManyConditionsInQuery
Code: 0x8004430C
Number: -2147204340
Message: Number of conditions in query exceeded maximum limit.

您需要减少执行查询的条件数量。您可以通过使用in操作符来减少条件的数量,该操作符可用于数字、唯一标识符和最多850个字符的字符串。

标签:entity,fetchXml,FetchXml,link,使用,using,查询,data
From: https://www.cnblogs.com/YuYangBlogs/p/18247367

相关文章

  • Dynamics CRM 365 使用 FetchXml 分页(Page results using FetchXml)
    介绍可以通过设置页面大小来指定对每个请求检索的行数的限制。通过使用分页,您可以检索连续的数据页,这些数据页表示符合查询条件的所有记录。默认和最大页面大小为5,000行。如果不设置页面大小,Dataverse将一次返回多达5000行数据。要获得更多行,必须发送额外的请求。不要将fetch......
  • Dynamics CRM 365 使用 FetchXml 聚合数据(Aggregate data using FetchXml)
    前言FetchXML包括分组和聚合功能,可用于计算多行数据的总和、平均值、最小值、最大值和计数。若要返回聚合值,必须:将aggregate设置为true。为每个属性元素设置别名alias属性。将每个属性元素的aggregate属性设置为以下聚合函数之一:函数返回值avg包含数据的......
  • DataGridView列填充实体类
    使用的地方:假如你有一个名为rgvProcessDtl的DataGridView控件DataTabledt=(DataTable)rgvProcessDtl.DataSource;foreach(DataRowrowindt){OG_ProcessGuidDtldtl=newOG_ProcessGuidDtl();FillModel(dtl,row);//将实体类对象与grid行填充}//////将数据填入实......
  • ETL可视化工具 DataX -- 简介( 一)
    引言DataX系列文章:ETL可视化工具DataX–安装部署(二)1.1DataX1.1.1DataX概览DataX是阿里云DataWorks数据集成的开源版本,在阿里巴巴集团内被广泛使用的离线数据同步工具/平台。DataX实现了包括MySQL、Oracle、OceanBase、SqlServer、Postgre、HDFS、Hive、A......
  • (pdf)数据结构与算法分析 Java语言描述=Data Structures and Algorithm Analysis in Jav
    书:pan.baidu.com/s/1tGbGhhQ3Ez1SIkqdEREsjQ?pwd=eqp0提取码:eqp0数组:作为最基本的数据结构,用于存储固定大小的同类型元素集合。链表:动态数据结构,允许在任意位置插入和删除元素。栈:后进先出(LIFO)的数据结构,常用于函数调用和表达式求值。队列:先进先出(FIFO)的数据结构,常用于任务调......
  • unitycatalog datagrics 开源的data&ai 多模catalog
    unitycatalogdatagrics开源的data&ai多模catalog包含的特性支持任意格式、引擎、资产的多摸接口 支持包含了deltalake,iceberg,uniform,paquert,csv。。。等格式,超越表,支持非结构化数据以及ai资产,插件化的架构,可以支持hms以及icebergrestcatalog以及其他插件(比如ai),与delt......
  • 一家令人艳羡的大数据AI公司!Databricks
    今日介绍一家大数据AI超级独角兽公司,以及它如何与当前生物基因组学相结合。它就是Databricks,没错,俗称“砖厂”。Databricks简介Databricks公司诞生于2013年,是属于Spark的商业化公司,创始人来自ApacheSpark大数据处理系统的创始团队,包括加州大学伯克利分校的AMP实验室。Databric......
  • WPF Path Data PathGeometry PathFigure Segments BezierSegment,LineSegment,ArcSeg
     BezierSegment//BezierCurveusingSystem;usingSystem.Collections.Generic;usingSystem.Linq;usingSystem.Text;usingSystem.Threading.Tasks;usingSystem.Windows;usingSystem.Windows.Controls;usingSystem.Windows.Data;usingSystem.Windows.Documen......
  • COMP20008 - Elements of Data Processing
    COMP20008- Elements of Data Processing, Semester 1,2024Assignment2–Whoelse likesthis book?1. OverviewIn thisproject, you willundertake an analysis of a collection of datasets containing detailed informationaboutbooksandt......
  • pandas ---- pd.DataFrame基本用法
    文章目录前言1loc和iloc注意事项。(后面这些都会在笔记中提到)2DataFrame的维度一、DataFrame的创建---pd.DataFrame(data,index=None,columns=None)1字典创建DataFrame(字典转Dataframe很常用)2用numpy数组或者嵌套list创建DataFrame二、DataFrame的......