某些应用程序受益于维护 Dataverse 组织的架构定义的持久缓存。 例如:
- 与 Dataverse 服务器断开连接时需要工作的应用程序。
- 对有限网络带宽敏感的应用程序,例如移动应用程序。
Dataverse 有很多架构定义数据,很少有应用程序必须跟踪所有这些数据。 限制要缓存的数据量至关重要。
该 RetrieveMetadataChanges 消息提供两项功能:
- 查询:编写单个查询以仅检索所需的架构数据。 撰写查询的内容在查询架构定义中进行了介绍。
-
缓存管理:如果将架构定义数据缓存到应用中,可以使用
RetrieveMetadataChanges有效地检索自上次查询以来的更改。 使用有关这些更改的信息在缓存中添加或删除项。 缓存架构数据可能会导致应用程序启动的显著改善时间,并且是本文的重点。
定义要缓存的架构数据的查询后,请使用消息的其他功能 RetrieveMetadataChanges 来创建和维护 Dataverse 架构数据的缓存。
创建缓存
如 查询架构定义中所述,第一步是创建定义你感兴趣的架构信息的类型的查询。
RetrieveMetadataChanges然后使用消息执行该查询并缓存应用程序中返回的架构定义。 找到一种方法来保存适合应用需求的此数据。 可以将其保存为应用程序启动时读取的文件。 还需要保存上次运行查询时的数据。
以对应用程序有意义的方式构建缓存。 若要管理删除已删除的项,缓存使用 MetadataId 的唯一标识符非常重要。 有关详细信息,请参阅 “删除已删除的项目”。
检测更改
不存在任何事件来检测架构定义更改的发生。 根据应用程序的需求刷新缓存。 通常,在应用程序启动时检索更改。 但是,如果您想检测随时间变化的情况,可能会定期轮询系统。 无论策略如何,请跟踪发送上一个请求的时间。
该 RetrieveMetadataChangesResponse.ServerVersionStamp 属性包含有关发生请求 RetrieveMetadataChanges 的时间点的信息。 使用上一个响应中的ServerVersionStamp值,并在使用同一查询再次发送时作为RetrieveMetadataChangesRequest.ClientVersionStamp的值。
在 ClientVersionStamp 请求中包含该属性时, RetrieveMetadataChangesResponse.EntityMetadata 返回的属性仅包含自上一个请求以来已更改或添加的架构数据。 可以将它们添加到缓存。
如果还包括 DeletedMetadataFilters 参数,那么自上一个请求以来删除的任何架构项都将包含在 RetrieveMetadataChangesResponse.DeletedMetadata 属性中。 可以从缓存中删除它们。
此结果比再次执行原始查询要小且更快。
管理过期的缓存
默认情况下,Dataverse 存储有关更改的信息 90 天。 此值存储在 Organization.ExpireSubscriptionsInDays 属性中。 如果您发送的请求中的 ClientVersionStamp 值早于设置值,Dataverse 将返回 ExpiredVersionStamp 错误(0x80044352)。 准备好处理此特定错误,并在错误发生时重新初始化缓存。
注释
即使你认为你的值始终小于 90 天,也请做好应对此错误的准备。 当服务器上的任何更改都影响准确跟踪已删除的架构数据时,会发生此错误。 例如,更改属性会使 Organization.ExpireSubscriptionsInDays 所有以前的 VersionStamp 值失效。 其中一些更改可能不是由你执行的作引起的,但可能是由系统维护触发的。
添加已更改的项目
正如执行初始查询来初始化缓存时一样,通过使用 RetrieveMetadataChangesRequest.ClientVersionStamp 返回的属性对于后续请求来说,仍包含已更改项的完整层次结构。
层次结构中的每个项都有可为 null 的布尔 HasChanged 值。 如果此值为 false,则表示当前项未更改,但在层次结构中其下方的内容已更改。
HasChanged如果值为 true,则表示层次结构中的当前项已更改。
注释
如果在查询中请求 EntityMetadata.Privileges ,则始终返回特权,无论它们是否更改。 特权通常不会更改。
跟踪选项
跟踪更改的一个区域似乎并不直观,即如何跟踪选择列的选项。 此区域是一个很好的示例,用于了解 HasChanged 属性。
向选项列添加新选项时,层次结构中的以下数据将通过 RetrieveMetadataChangesResponse.EntityMetadata 属性返回:
-
EntityMetadataCollection
-
EntityMetadata:表定义。
-
EntityMetadata.Attributes[]
-
EnumAttributeMetadata:Choice 列的基类。
-
EnumAttributeMetadata.OptionSet
-
OptionSetMetadata:
HasChanged为 true。-
OptionSetMetadata.Options:返回所有选项。
-
OptionMetadata
- OptionMetadata.Color:如果已设置,则只有新选项具有值。
- OptionMetadata.Label:只有新选项具有值。
- OptionMetadata.Value:始终具有值。
- OptionMetadata.HasChanged:值为 null。
-
OptionMetadata
-
OptionSetMetadata.Options:返回所有选项。
-
OptionSetMetadata:
-
EnumAttributeMetadata.OptionSet
-
EnumAttributeMetadata:Choice 列的基类。
-
EntityMetadata.Attributes[]
-
EntityMetadata:表定义。
你知道,由于 HasChanged 属性为 false,EntityMetadata 和 EnumAttributeMetadata 未更改。 只有属性 OptionSetMetadata.HasChanged 为 true。 返回所有当前有效选项。
OptionMetadata.HasChanged所有选项(包括新选项)的属性为 null。
只有新创建的选项才包含 Label 属性的数据。 仅当其属性之一(如Color或Label)发生更改时,OptionMetadata.HasChanged属性才为 true。
删除已删除的项目
当为 RetrieveMetadataChanges 消息同时包含 ClientVersionStamp 和 DeletedMetadataFilters 参数时,该 RetrieveMetadataChangesResponse.DeletedMetadata 属性包含有关任何已删除项的数据。 此属性是 DeletedMetadataCollection,并包含一组 Keys 和 Values。 这些键是 DeletedMetadataFilters 枚举值,可以使用这些值来访问已删除值的子集。
注释
DeletedMetadataFilters 参数是可选的。 包括它可能会影响性能,因为进程直接从数据库而不是内部缓存中检索数据。 仅当必须检测已删除的项并将筛选器值设置为返回的最小数据量时,才使用它。
已删除的值作为 Guid 值的集合返回。 已删除项的值不会根据查询进行筛选。 许多 Guid 值不在缓存中,但缓存项的 Guid 值已包含。 必须查找任何匹配 Guid 的值并删除这些项。 忽略缓存中未包含的任何值。
注释
Web API DeletedMetadataFilters 枚举类型 的定义与 SDK DeletedMetadataFilters 枚举 略有不同。
Web API DeletedMetadataFilters EnumType 没有该 Entity 成员。 请改用 Default。
跟踪已删除的选项
请注意,DeletedMetadataFilters 枚举中包含一个用于OptionSet的成员,但不包含选项。 如果从选择列中删除任何选项,则找不到对已删除的特定选项的引用。 你需要转到缓存选项,并将其与该OptionSet返回的当前选项进行比较。
另请参阅
Web API 查询架构定义和检测更改示例 (C#)
用于 .NET 的 SDK:查询架构定义并检测更改的示例程序(C#)
查询架构定义