资讯详情

Envoy Load-Aware Locality 负载均衡策略:基于 ORCA 利用率余量的 locality 感知路由

📅 2026/9/12 16:09:09 | 华诺云谱 👁 阅读
Envoy Load-Aware Locality 负载均衡策略:基于 ORCA 利用率余量的 locality 感知路由
Envoy Load-Aware Locality 负载均衡策略基于 ORCA 利用率余量的 locality 感知路由【免费下载链接】envoyCloud-native high-performance edge/middle/service proxy项目地址: https://gitcode.com/GitHub_Trending/en/envoy导读Envoy 在负载均衡领域引入了envoy.load_balancing_policies.load_aware_localityLoad-Aware Locality-Picking负载均衡策略它不再依赖静态的 locality 权重配置而是通过 ORCAOpen Request Cost Aggregation上报的利用率数据计算每个 locality 的可用余量headroom据此在多个 zone/region 之间动态分配流量并且适用于所有 priority 级别。读完本文你将掌握该策略的配置字段与默认值、基于 ORCA 利用率的权重计算与 EWMA 平滑原理、本地优先与远端探测机制以及当前实现的适用边界官方标注为 work-in-progress不建议生产使用。该策略在 changelog 中登记为load_balancing: implemented the envoy.load_balancing_policies.load_aware_locality locality-picking load balancer见 changelogs/current/new_features/load_balancing__load-aware-locality-lb-policy.rst属于new features列表中的一项新增能力。一、策略定位从按配置权重到按利用率余量传统的 zone-aware 负载均衡依赖管理员为每个 locality 配置静态权重或依靠调度器下发权重而 Load-Aware Locality 的思路是数据来源消费 ORCA 上报的负载报告默认走逐请求的 in-band 上报也可开启 out-of-band 上报核心指标以 ORCA 推导出的利用率utilization为基准计算每个 locality 的剩余容量headroom即1 - utilization决策粒度先按利用率余量为 locality 分配权重选定 locality 之后再交给内部的 child LB 策略在 host 级别做端点选择适用范围在所有 priority 级别all priority levels上都生效而非仅作用于最高优先级。从扩展注册信息看该策略在 source/extensions/extensions_metadata.yaml 中以envoy.load_balancing_policies.load_aware_locality名称注册对应的 proto 消息为envoy.extensions.load_balancing_policies.load_aware_locality.v3.LoadAwareLocality。需要特别强调的是changelog 与本仓库源码均明确标注该扩展为work-in-progress 且不用于生产环境The extension is work-in-progress and not intended for production use读者在选型时应留意这一前提。二、配置详解proto 字段、默认值与校验规则策略配置定义在 api/envoy/extensions/load_balancing_policies/load_aware_locality/v3/load_aware_locality.proto共 9 个可配置字段。下面是完整字段表字段类型默认值校验规则说明endpoint_picking_policyconfig.cluster.v3.LoadBalancingPolicy无必填required每个 locality 内部做端点选择的 child LB 策略weight_update_periodgoogle.protobuf.Duration1s至少 100ms主线程上重算 ORCA 权重与 locality 利用率的周期metric_names_for_computing_utilizationrepeated string空—用于计算端点利用率的 ORCA 指标名列表utilization_variance_thresholdgoogle.protobuf.DoubleValue0.1[0, 1]本地利用率相对远端平均值低于该阈值时100% 流量留在本地smoothing_time_constantgoogle.protobuf.Duration5s 0slocality 利用率 EWMA 平滑时间常数remote_probe_fractiongoogle.protobuf.DoubleValue0.03[0, 1)为保证 ORCA 数据新鲜度而分给远端 locality 的最小流量比例weight_expiration_periodgoogle.protobuf.Duration3 分钟≥ 0s单 host ORCA 样本的有效窗口0s 表示不失效enable_oob_load_reportgoogle.protobuf.BoolValuefalse—是否开启端点的 out-of-band 利用率上报默认逐请求上报oob_reporting_periodgoogle.protobuf.Duration10s—请求服务端上报的间隔仅当enable_oob_load_report为 true 时生效以上默认值与校验规则并非仅存在于 proto 注释中——config.cc 的Factory::loadConfig逐项落实了这些约束weight_update_period不足 100ms 时报InvalidArgumentError(weight_update_period must be at least 100ms)smoothing_time_constant必须为正utilization_variance_threshold必须在 [0,1] 区间remote_probe_fraction必须在 [0,1)。对应测试 config_test.cc 中的LoadAwareLocalityConfigTest.Defaults也验证了默认值weightUpdatePeriod() 1000ms、utilizationVarianceThreshold() 0.1、remoteProbeFraction() 0.03、weightExpirationPeriod() 180000ms。2.1 关键字段的语义细节metric_names_for_computing_utilization利用率来源对于 ORCA proto 中的 map 类型字段字符串形如map_field_name.map_key例如named_metrics.foo表示取 ORCAnamed_metrics字段中 key 为foo的值。利用率的取值优先级为先取本列表指定指标中大于 0 的最大值若都不大于 0则回退到application_utilization再回退到cpu_utilization。此外还存在一个运行时开关envoy.reloadable_features.orca_weight_manager_use_named_metrics_first见 source/common/runtime/runtime_features.cc 中的RUNTIME_GUARD声明禁用该开关可恢复旧优先级顺序即优先使用application_utilization而非 named metrics。utilization_variance_threshold本地偏好阈值当本地 locality 的利用率至多比远端平均利用率高该阈值时100% 的流量路由到本地从而避免在负载基本均衡时产生不必要的跨 zone 流量。该判断是单向的若本地 zone 负载低于远端则始终全本地路由。实现位于computeSourceWeights当utilizations[0] target_util utilization_variance_threshold_时置local_preferred并将全部权重收敛到本地。smoothing_time_constantEWMA 平滑每个 tick 的平滑因子alpha 1 - exp(-weight_update_period / smoothing_time_constant)。由于 alpha 由 tick 周期与时间常数共同推导无论配置多快的更新周期settling 时间保持一致默认 5s 常数下约 95% 在约 15s 内收敛。更大的值权重更稳定、反应更慢更小的值反应更快。该推导在 config.cc 中实现ewma_alpha 1.0 - std::exp(-weight_update_period / smoothing_time_constant)。remote_probe_fraction远端探测流量当本地偏好判断会导致 100% 流量留在本地时为保证 ORCA 数据不陈旧需要保留一小部分流量打到远端 locality。该比例是全局值会按 host 数量比例拆分到所有远端 locality注意探针比例是全局值分摊到所有远端 locality——在远端 locality 数量非常多且总请求率很低时单个 host 的采样间隔可能超过weight_expiration_periodproto 注释提到架构总览中给出了扩展性矩阵。设为 0 可关闭但仅当 ORCA 报告以 out-of-band 方式到达、或必须严格避免跨 zone 流量时才安全。weight_expiration_period样本有效期host 在该时长内没有上报负载指标则被排除出其 locality 的利用率聚合。locality 的 EWMA 状态会在剩余上报 host 上继续正常演进。若某个 locality 的全部 host 都过期该 locality 回退到按 host 数量成比例的权重与所有 locality 过载时的路径相同。设为 0s 关闭过期机制。三、完整的 YAML 配置示例下面是在 cluster 上启用该策略的最小可运行配置children 使用 round_robin 作为 locality 内部端点选择器load_balancing_policy: policies: - typed_extension_config: name: envoy.load_balancing_policies.load_aware_locality typed_config: type: type.googleapis.com/envoy.extensions.load_balancing_policies.load_aware_locality.v3.LoadAwareLocality endpoint_picking_policy: policies: - typed_extension_config: name: envoy.load_balancing_policies.round_robin typed_config: type: type.googleapis.com/envoy.extensions.load_balancing_policies.round_robin.v3.RoundRobin weight_update_period: 1s utilization_variance_threshold: 0.1 smoothing_time_constant: 5s remote_probe_fraction: 0.03 weight_expiration_period: 180s metric_names_for_computing_utilization: - named_metrics.foo # enable_oob_load_report: true # oob_reporting_period: 10s在 integration_test.cc 的集成测试中可以看到该策略的完整装配方式测试将 node 的 locality 设置为regiontest-region, zonezone-a在load_assignment下同时配置本地 zonezone-a与远端 zonezone-b的 locality 分组再通过load_balancing_policy挂载上述策略从而验证跨 zone 场景下的路由行为。这也提示了一个部署前提该策略依赖端点配置中 locality 分组信息load_assignment.endpoints[].locality本地 locality 由 Envoy 自身所在 zone 判定。四、实现原理主线程算权重Worker 线程选端点从源码结构看该扩展的实现是典型的主线程/工作线程分工模型核心类位于 load_aware_locality_lb.h 与 load_aware_locality_lb.cc主线程LoadAwareLocalityLoadBalancer实现ThreadAwareLoadBalancer通过定时器周期性地执行computeLocalityRoutingWeights()把所有 priority、所有 SelectionSourceHealthy / Degraded / AllHosts下的 locality 权重算好后以RoutingWeightsSnapshot快照形式通过 TLSThreadLocalShim发布到各 workerWorker 线程WorkerLocalLb继承LoadBalancerBase维护每个 locality 的 child LBPerLocalityState每次选路时先做 live 的 priority/健康度选择resolvePrioritySource再按发布的权重快照选择 localitychooseLocality最后把请求委托给该 locality 的 child LB 完成端点选择chooseHost。4.1 权重计算host 数 × (1 - utilization)computeSourceWeights是权重计算的核心load_aware_locality_lb.cc对每个 locality遍历其健康/降级/全部 host读取每个 host 的 ORCA 利用率过滤掉从未上报kNeverReported或已超过weight_expiration_period的过期 host求平均得到avg_utils[i]用 EWMA 平滑smoothed alpha * avg_utils[i] (1 - alpha) * prev平滑后的利用率存入LocalityEwmaMap以 locality 身份为 key避免 host 增删导致的下标错位计算基础权重weight host_count * max(0.0, 1.0 - utilization)——即利用率余量headroom越大、host 越多权重越高无有效样本stale的 locality 直接退化为host_count三种退化/修正路径全过载all_overloaded若总基础权重为 0 且存在 host回退为按 host 数量成比例分配本地偏好local_preferred本地利用率 ≤ 远端加权平均利用率 阈值时全部权重收敛到本地all_local远端探测probe_active若远端权重占比低于remote_probe_fraction从本地权重中切出一部分按远端 host 数量比例重新分配。4.2 ORCA 上报数据的消费与新鲜度每个 host 的负载数据存放在LocalityLbHostData实现HostLbPolicyData中worker 线程调用onOrcaLoadReport写入利用率主线程读取。跨线程写入通过std::atomicdouble与std::atomicMonotonicTime完成代码中有static_assert保证两个原子类型都是无锁的lock-free。值得注意的是无利用率信号util 0.0的报告不会刷新 freshness 时间戳从而让静默 host 自然过期而不是钉住空闲状态。底层 ORCA 处理复用能力来自 source/extensions/load_balancing_policies/common/orca_weight_manager.hOrcaLoadReportHandler::getUtilizationFromOrcaReport()负责从xds.data.orca.v3.OrcaLoadReport中按metric_names_for_computing_utilization提取利用率OrcaWeightManager原本从 ClientSideWeightedRoundRobin 中抽取、供多个 LB 策略复用。本策略的 host 数据仅存利用率与时间戳不做 QPS/EPS 加权这是它与 client_side_weighted_round_robin 的差异点。4.3 每次选路一次随机、两步决策Worker 端每次选路只消耗一次随机数resolvePrioritySource中random(peeking)priority/健康度选择与 locality 选择共享该随机数locality 目标通过splitMix64(hash)二次派生黄金比例递增 收尾混合使两个决策相互独立。权重快照在发布时即被转换为按 locality 下标的前缀和数组refreshLocalityWeights选路时用std::upper_bound二分查找完成避免逐次哈希 locality 身份快照与拓扑不一致时如 child LB 因 host 变更被拆除pickLocalityLb会从下一个下标开始环绕扫描可用的 child LB避免并发 drain 全部压到同一个 locality。4.4 可观测性专用计数器主线程每次重算都会更新以下计数器定义于 load_aware_locality_lb.h统计名前缀为load_aware_locality计数器语义recompute_total权重重算总次数all_overloaded_total出现全过载回退的 tick 数local_preferred_total触发本地偏好全本地路由的 tick 数probe_active_total远端探测流量生效的 tick 数spill_active_total本地负载过高、向外溢出的 tick 数stale_locality_total累计的陈旧 locality 计数此外 Worker 端复用标准 zone 路由统计lb_zone_routing_cross_zone、lb_zone_routing_all_directly、lb_zone_routing_sampled来区分跨 zone、全直达与被采样的路由见recordZoneRoutingStats。五、边界条件与适用前提官方状态该扩展为 work-in-progresschangelog 与代码注释均明确不用于生产环境评估与选型时请以这一状态为准配置校验细节endpoint_picking_policy是必填项且不允许嵌套自身load_aware_locality cannot be its own endpoint_picking_policy避免统计重复注册与 metric 丢失若无法实例化 child 策略集群初始化会失败Unsupported endpoint picking policy for load_aware_locality: ...从而不会进入 worker 阶段见 config.cc 与 load_aware_locality_lb.cc数据新鲜度与探针比例的权衡默认 3% 的远端探针流量是全局值跨 zone 流量被严格禁止的部署需要显式置 0仅当 ORCA 走 out-of-band 上报时安全远端 locality 数量多而请求量低时需参照weight_expiration_period与采样矩阵调整参数依赖 ORCA 上报链路默认逐请求in-band上报要求端点侧能够随 RPC 响应携带 ORCA 负载报告如需降低 per-request 开销可开启enable_oob_load_report并配合oob_reporting_period服务端实际上报频率可能低于请求值。六、结语envoy.load_balancing_policies.load_aware_locality是 Envoy 在 locality 级负载均衡上的一次新尝试它把 ORCA 利用率数据、EWMA 平滑、本地偏好阈值与远端探测机制组合成一套按剩余容量路由的 locality 选择策略并在所有 priority 级别生效。其主线程计算/Worker 执行的架构、基于前缀和与二分查找的选路路径、以及完善的统计埋点为后续在生产环境打磨提供了清晰的实现基础。读者可结合 api 侧 proto 定义、主实现 以及 config 测试、集成测试 继续深入验证其行为。【免费下载链接】envoyCloud-native high-performance edge/middle/service proxy项目地址: https://gitcode.com/GitHub_Trending/en/envoy创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
📝

华诺云谱内容团队

资深建站顾问 · 行业研究员

10年+企业数字化服务经验,专注智能建站、SEO优化与品牌营销,持续输出建站技巧、行业洞察与营销干货,已帮助5000+企业实现数字化增长。

你可能需要的服务

订阅华诺云谱资讯周报

每周一封,精选建站技巧、SEO与营销干货,直达邮箱。已有 8,000+ 企业主订阅,助你少走弯路。