Kubernetes中的有状态服务的分片负载平衡 [英] Sharded load balancing for stateful services in Kubernetes

查看:81
本文介绍了Kubernetes中的有状态服务的分片负载平衡的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我目前正在从Service Fabric切换到Kubernetes,并且想知道如何进行自定义和更复杂的负载平衡.

到目前为止,我已经阅读了有关Kubernetes提供服务"的信息,该服务可以对隐藏在其后的Pod进行负载平衡,但这只能以更简单的方式提供.

我现在要重写的内容在Service Fabric中如下所示:

我有这个界面:

 公共接口IEndpointSelector{int HashableIdentifier {get;}} 

在我的ASP.Net应用程序中跟踪帐户的上下文,例如继承这个.然后,我编写了一些代码,到目前为止,这些代码将通过服务结构集群API进行服务发现,并跟踪所有服务,并在任何实例死亡或被重新生成时更新它们.

然后,基于此标识符的确定性(由于缓存了上下文等),并给出了前端目标服务的多个副本->后端调用,我可以将某个帐户的流量可靠地路由到某些终结点实例.

现在,我将如何在Kubernetes中做到这一点?

正如我已经提到的,我找到了服务",但是它们的负载平衡似乎不支持自定义逻辑,而仅在处理无状态实例时才有用.

在Kubernetes中是否还有一种服务发现的方法,我可以在这里用来替换现有代码?

解决方案

StatefulSet

StatefulSet 构建模块Kubernetes上有状态的工作负载,并且有一定的保证.

稳定且唯一的网络身份

StatefulSet Pod具有由序号,稳定的网络身份和稳定的存储组成的唯一身份.

例如,如果您的StatefulSet名称为 sharded-svc

  apiVersion:apps/v1种类:StatefulSet元数据:名称:sharded-svc 

例如3个副本,这些副本将由< name>-< ordinal> 命名,其中 ordinal 从0开始到副本1.

您的广告连播名称为:

  sharded-svc-0分片-svc-1分片-svc-2 

,并且可以使用dns名称访问这些吊舱:

  sharded-svc-0.sharded-svc.your-namespace.svc.cluster.localsharded-svc-1.sharded-svc.您的命名空间.svc.cluster.localsharded-svc-2.sharded-svc.您的命名空间.svc.cluster.local 

假设您的 Headless Service 被命名为 sharded-svc ,并将其部署在名称空间 your-namespace 中.

共享或分区

考虑到前端目标服务的多个副本->后端调用,我可以可靠地将某个帐户的流量路由到某个终结点实例.

您在这里描述的是,您的有状态服务就是所谓的 sharded partitioned .Kubernetes并没有开箱即用,但是您已经具备了所有需要的构建基块来进行这种服务.可能会存在一个第三方服务,该服务可提供您可以部署的功能,也可以对其进行开发.

共享代理

您可以创建由多个Pod之一组成的服务 sharding-proxy (可能来自端点sharded-svc 知道它可以将流量路由到何处.可以使用 client-go 或其他替代方法进行开发.

此服务可实现您在分片中所需的逻辑,例如 account-nr 模数3被路由到相应的pod ordinal

更新:存在具有 sharding 功能的第三方代理,例如 Weaver代理

基于标题/路径/正文字段的共享请求

推荐阅读: Weaver:简单的分片

使用分片服务

要使用您的分片服务,客户端会将请求发送到您的 sharding-proxy ,然后应用您的 routing sharding逻辑(例如,请求具有 account-nr 模数3的路由发送到相应的Pod(emordinal ),并将请求转发给 sharded-svc 与您的逻辑相符.

替代解决方案

目录服务:将 sharded-proxy 实现为目录服务可能会更容易,但这取决于您的要求.客户可以询问您的目录服务我应该向哪个statefulSet副本发送 account-nr X ,您的服务答复例如 sharded-svc-2

客户端中的路由逻辑:可能最简单的解决方案是在客户端中使用路由逻辑,然后让该逻辑计算到哪个statefulSet副本发送请求

I am currently switching from Service Fabric to Kubernetes and was wondering how to do custom and more complex load balancing.

So far I already read about Kubernetes offering "Services" which do load balancing for pods hidden behind them, but this is only available in more plain ways.

What I want to rewrite right now looks like the following in Service Fabric:

I have this interface:

public interface IEndpointSelector
{
    int HashableIdentifier { get; }
}

A context keeping track of the account in my ASP.Net application e.g. inherits this. Then, I wrote some code which would as of now do service discovery through the service fabric cluster API and keep track of all services, updating them when any instances die or are being respawned.

Then, based on the deterministic nature of this identifier (due to the context being cached etc.) and given multiple replicas of the target service of a frontend -> backend call, I can reliably route traffic for a certain account to a certain endpoint instance.

Now, how would I go about doing this in Kubernetes?

As I already mentioned, I found "Services", but it seems like their load balancing does not support custom logic and is rather only useful when working with stateless instances.

Is there also a way to have service discovery in Kubernetes which I could use here to replace my existing code at some points?

解决方案

StatefulSet

StatefulSet is a building block for stateful workload on Kubernetes with certain guarantees.

Stable and unique network identity

StatefulSet Pods have a unique identity that is comprised of an ordinal, a stable network identity, and stable storage.

As an example, if your StatefulSet has the name sharded-svc

apiVersion: apps/v1
kind: StatefulSet
metadata:
  name: sharded-svc

And you have e.g. 3 replicas, those will be named by <name>-<ordinal> where ordinal starts from 0 up to replicas-1.

The name of your pods will be:

sharded-svc-0
sharded-svc-1
sharded-svc-2

and those pods can be reached with a dns-name:

sharded-svc-0.sharded-svc.your-namespace.svc.cluster.local
sharded-svc-1.sharded-svc.your-namespace.svc.cluster.local
sharded-svc-2.sharded-svc.your-namespace.svc.cluster.local

given that your Headless Service is named sharded-svc and you deploy it in namespace your-namespace.

Sharding or Partitioning

given multiple replicas of the target service of a frontend -> backend call, I can reliably route traffic for a certain account to a certain endpoint instance.

What you describe here is that your stateful service is what is called sharded or partitioned. This does not come out of the box from Kubernetes, but you have all the needed building blocks for this kind of service. It may happen that it exists an 3rd party service providing this feature that you can deploy, or it can be developed.

Sharding Proxy

You can create a service sharding-proxy consisting of one of more pods (possibly from Deployment since it can be stateless). This app need to watch the pods/service/endpoints in your sharded-svc to know where it can route traffic. This can be developed using client-go or other alternatives.

This service implements the logic you want in your sharding, e.g. account-nr modulus 3 is routed to the corresponding pod ordinal

Update: There are 3rd party proxies with sharding functionallity, e.g. Weaver Proxy

Sharding request based on headers/path/body fields

Recommended reading: Weaver: Sharding with simplicity

Consuming sharded service

To consume your sharded service, the clients send request to your sharding-proxy that then apply your routing or sharding logic (e.g. request with account-nr modulus 3 is routed to the corresponding pod ordinal) and forward the request to the replica of sharded-svc that match your logic.

Alternative Solutions

Directory Service: It is probably easier to implement sharded-proxy as a directory service but it depends on your requirements. The clients can ask your directory service to what statefulSet replica should I send account-nr X and your serice reply with e.g. sharded-svc-2

Routing logic in client: The probably most easy solution is to have your routing logic in the client, and let this logic calculate to what statefulSet replica to send the request.

这篇关于Kubernetes中的有状态服务的分片负载平衡的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆