优化业务规则引擎 (BRE) 性能

在 BizTalk Server 解决方案中实现业务规则引擎(BRE)时,应考虑以下因素:

事实类型

与访问 XML 和数据库事实所需的时间相比,规则引擎访问 .NET 事实所需的时间更少。 如果选择在策略中使用 .NET 或 XML 或数据库事实,应考虑使用 .NET 事实来提高性能。

数据表与数据连接

当数据集的大小较小(< 10 左右)时, TypedDataTable 绑定比 DataConnection 绑定提供更好的性能。 但是,当数据集较大(大约大于或等于 10 行)时, DataConnection 绑定的性能优于 TypedDataTable 绑定。 因此,应根据数据集的估计大小决定是使用 DataConnection 绑定还是 TypedDataTable 绑定。

事实检索器

事实检索器实现标准方法,这些方法通常用于在执行策略之前向规则引擎提供长期且缓慢地更改事实。 引擎将缓存这些事实,并在多个执行循环中使用它们。 每次调用规则引擎时,不应提交静态或相当静态的事实,而是应创建一个事实检索器,该检索器首次提交事实,然后仅在必要时更新内存中的事实。

规则优先级

规则的优先级设置可以在 0 的两侧变化,数字越大表示优先级越高。 动作按优先级从高到低的顺序执行。 当策略使用 Assert/Update 调用实现正向推理行为时,可以通过使用优先级设置来优化推理过程。 例如,假设 Rule2 依赖于 Rule1 设置的值。 为 Rule1 提供更高的优先级意味着 Rule2 仅在 Rule1 触发并更新值后才会执行。 相反,如果 Rule2 具有更高的优先级,则它可以触发一次,然后在 Rule1 触发后再次触发并更新 Rule2 正在使用条件的事实。 虽然这可能会提供正确的结果,但在此方案中为 Rule1 提供更高的优先级将提供更好的性能。

Update 调用

Update 函数会导致使用更新的事实重新评估所有规则。 更新函数调用可能会非常昂贵,尤其是在更新事实过程中需要重新评估大量规则时。 在某些情况下,可以避免此行为。 例如,请考虑以下规则。

规则 1:

IF PurchaseOrder.Amount > 5   
THEN StatusObj.Flag = true; Update(StatusObj)  

规则 2:

IF PurchaseOrder.Amount <= 5   
THEN StatusObj.Flag = false; Update(StatusObj)  

策略的所有剩余规则在其条件中使用 StatusObj.Flag 。 因此,在 StatusObj 对象上调用 Update 时,将重新评估所有规则。 无论Amount字段的值是什么,排除Rule1Rule2之外的所有规则都会被评估两次:一次是在更新调用之前,另一次是在更新调用之后。

若要缓解关联的开销,可以在调用策略之前将 标志 字段的值设置为 false ,然后在策略中仅使用 Rule1 设置标志。 在这种情况下,只有在 Amount 字段的值大于 5 时,才会调用 Update,如果 Amount 的值小于或等于 5,则不会调用 Update 函数。 因此,仅当 Amount 字段的值大于 5 时,除 Rule1Rule2 之外的所有规则都会计算两次。

逻辑 OR 运算符的用法

在条件中使用越来越多的逻辑 OR 运算符可创建扩展规则引擎分析网络的附加排列。 从性能的角度来看,最好将条件拆分为不包含逻辑 OR 运算符的原子规则。

缓存设置

规则引擎使用两个缓存。 第一个由更新服务使用,第二个由每个 BizTalk 进程使用。 首次使用策略时,BizTalk 进程会从更新服务请求策略信息。 更新服务从规则引擎数据库中检索策略信息,将其缓存,并将信息返回到 BizTalk 进程。 BizTalk 进程基于该信息创建策略对象,并在关联的规则引擎实例完成策略执行时将策略对象存储在缓存中。 再次调用同一策略时,BizTalk 进程会重复使用缓存中的策略对象(如果有)。 同样,如果 BizTalk 进程从更新服务请求有关策略的信息,则更新服务会在其缓存中查找策略信息(如果可用)。 每隔 60 秒,更新服务还会检查数据库中是否有策略的任何更新。 如果有任何更新,更新服务将检索信息并缓存更新的信息。

规则引擎有三个与这些缓存相关的优化参数: CacheEntriesCacheTimeoutPollingInterval。 可以在注册表或配置文件中指定这些参数的值。 CacheEntries 参数的值是缓存中的最大条目数,默认情况下设置为值 32。 你可能希望增加 CacheEntries 参数的值,以提高在某些情况下的性能。 例如,假设重复使用 40 个策略;可以将 CacheEntries 参数的值增加到 40 以提高性能。 这将允许更新服务在内存中维护最多 40 个策略的缓存详细信息。

CacheTimeout 的值是更新服务缓存中维护项的时间(以秒为单位)。 换句话说,CacheTimeout 值指的是缓存中的策略条目在未被引用时所保存的时间。 CacheTimeout 参数的默认值为 3600 秒或 1 小时。 这意味着,如果在一小时内未引用缓存项,则会删除该条目。 在某些情况下,增加 CacheTimeout 参数的值以提高性能可能很有帮助。 例如,如果每隔两小时调用一个策略,则会通过将 CacheTimeout 参数增加到大于两小时的值来提高策略执行的性能。

规则引擎的 PollingInterval 参数定义更新服务检查规则引擎数据库是否有更新的时间(以秒为单位)。 PollingInterval 参数的默认值为 60 秒。 如果知道策略根本不更新或很少更新,则可以将此参数更改为更高的值以提高性能。

SideEffects 属性

ClassMemberBindingDatabaseColumnBindingXmlDocumentFieldBinding 类具有名为 SideEffects 的属性。 此属性用于确定绑定字段、成员或列的值是否被缓存。 DatabaseColumnBindingXmlDocumentFieldBinding 类中的 SideEffects 属性的默认值为 falseClassMemberBinding 类中 SideEffects 属性的默认值为 true。 因此,在策略中第二次或之后访问 XML 文档或数据库表列的字段时,将从缓存中检索其值。 但是,第二次或以后访问 .NET 对象的成员时,该值将从 .NET 对象中检索,而不是从缓存中检索。 将 .NET ClassMemberBindingSideEffects 属性设置为 false 会提高性能,因为该字段的值将从第二次开始从缓存中检索。 你只能以编程方式执行此操作。 业务规则编辑器工具不公开 SideEffects 属性。

Instances 和 selectivity

XmlDocumentBindingClassBindingDatabaseBinding 类具有两个属性:实例选择性。 Instances 的值是工作内存中类的预期实例数。 Selectivity 的值是成功传递规则条件的类实例的百分比。 规则引擎使用这些值来优化条件评估,以便先在条件评估中使用最少的实例,然后使用剩余实例。 如果事先知道对象的实例数,将 Instances 属性设置为该值可以提高性能。 同样,如果事先知道这些对象传递条件的百分比,请将 Selectivity 属性设置为该值可以提高性能。 只能以编程方式设置这些参数的值。 业务规则编辑器工具不公开它们。

另请参阅

优化 BizTalk Server 性能