Kubenetes:是否可以在Kubernetes群集中使用单个请求击中多个POD



我想在kubernetes名称空间中的所有吊舱中清除缓存。我想将一个请求发送到终点,然后将HTTP调用发送给名称空间中的所有POD,以清除缓存。目前,我只能使用Kubernetes击中一个POD,并且无法控制哪个POD会被击中。

,即使将负载范围设置为RR,也不断击中POD(n次,n是pod的总数(也无济于事,因为其他某些请求可能会渗入。

这里讨论了同样的问题,但我找不到实施的解决方案:https://github.com/kubernetes/kubernetes/issues/18755

我正在尝试使用Hazelcast实现清除缓存部分,其中我将自动存储所有的缓存和Hazelcast。

如果此问题有另一种方法,或者是一种配置Kubernetes以达到所有端点的方法,则在这里共享将是一个很好的帮助。

,只要您在吊舱中有kubectl并可以访问API-Server,您就可以得到所有端点Adressess并将其传递给卷发:

kubectl get endpoints <servicename> 
        -o jsonpath="{.subsets[*].addresses[*].ip}" | xargs curl

pod中没有kubectl的替代方案:

从POD访问API服务器的推荐方法是使用Kubectl代理:https://kubernetes.io/docs/tasks/Access-Application-cllication-cluster/access-cels/access-cluster/#accessing-the-accessing-the-api-from-the-api-from-a-pod当然会添加至少相同的开销。另外,您可以直接致电RETS API,必须手动提供令牌。

APISERVER=$(kubectl config view --minify | grep server | cut -f 2- -d ":" | tr -d " ")
TOKEN=$(kubectl describe secret $(kubectl get secrets 
     | grep ^default | cut -f1 -d ' ') | grep -E '^token' | cut -f2 -d':' | tr -d " ")

如果您提供了apiserver和令牌变量,则不需要吊舱中的kubectl,因此,您只需要curl即可访问API服务器,并且" JQ"来解析JSON输出:

curl $APISERVER/api/v1/namespaces/default/endpoints --silent 
     --header "Authorization: Bearer $TOKEN" --insecure 
     | jq -rM ".items[].subsets[].addresses[].ip" | xargs curl

更新(最终版本(

apiserver通常可以设置为kubernetes.default.svc,而代币则应在吊舱中在/var/run/secrets/kubernetes.io/serviceaccount/token上可用,因此无需手动提供任何东西:>

TOKEN=$(cat /var/run/secrets/kubernetes.io/serviceaccount/token); 
curl https://kubernetes.default.svc/api/v1/namespaces/default/endpoints --silent 
     --header "Authorization: Bearer $TOKEN" --insecure 
     | jq -rM ".items[].subsets[].addresses[].ip" | xargs curl

JQ可在此处找到:https://stedolan.github.io/jq/download/(&lt; 4 MIB,但值得以轻松解析JSON(

更新我为此方法发布了本文

我也有类似的情况。这是我解决的方式(我使用的是"默认值"以外的名称空间。

使用RBAC授权

设置群集访问群集

通过创建A serviceaccount ,将其分配给 pod 并将a 角色绑定到它。

1.创建A ServiceAccount

apiVersion: v1
kind: ServiceAccount
metadata:
  name: my-serviceaccount
  namespace: my-namespace

2.创建a 角色:在本节中,您需要提供资源列表和要访问的操作列表。这是您想列出端点并获取特定端点的详细信息的示例。

apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: my-role
  namespace: my-namespace
rules:
- apiGroups: [""]
  resources: ["endpoints"]
  verbs: ["get", "list"]

3.将角色结合到服务帐户

apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: my-role-binding
  namespace: my-namespace
subjects:
- kind: ServiceAccount
  name: my-serviceaccount
roleRef:
  kind: Role
  name: my-role
  apiGroup: rbac.authorization.k8s.io

4.将服务帐户分配给部署中的POD(应该在template.spec下(

apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-deployment
  namespace: my-namespace
spec:
  replicas: 1
  selector:
    matchLabels:
          app: my-pod
  template:
    metadata:
      labels:
        app: my-pod
    spec:
      serviceAccountName: my-serviceaccount
      containers:
      - name: my-pod
        ...

使用kubernetes api

访问簇

设置了所有安全性方面,您将有足够的特权访问POD中的API。与API服务器通信的所有必需信息都安装在您的POD中的/var/run/secrets/kubernetes.io/serviceaccount下。您可以使用以下Shell脚本(可能将其添加到Docker Image的命令或入口点(。

#!/bin/bash
# Point to the internal API server hostname
API_SERVER=https://kubernetes.default.svc
# Path to ServiceAccount token
SERVICE_ACCOUNT=/var/run/secrets/kubernetes.io/serviceaccount
# Read this Pod's namespace
NAMESPACE=$(cat ${SERVICE_ACCOUNT}/namespace)
# Read the ServiceAccount bearer token
TOKEN=$(cat ${SERVICE_ACCOUNT}/token)
# Reference the internal certificate authority (CA)
CA_CERT=${SERVICE_ACCOUNT}/ca.crt

从这一点开始,这只是简单的REST API调用。您可以使用您选择的任何语言阅读这些环境变量,并访问API。

这是列出用例的端点

的示例
# List all the endpoints in the namespace that Pod is running
curl --cacert ${CA_CERT} --header "Authorization: Bearer ${TOKEN}" -X GET 
  "${API_SERVER}/api/v1/namespaces/${NAMESPACE}/endpoints"
# List all the endpoints in the namespace that Pod is running for a deployment
curl --cacert ${CA_CERT} --header "Authorization: Bearer ${TOKEN}" -X GET 
  "${API_SERVER}/api/v1/namespaces/${NAMESPACE}/endpoints/my-deployment"

有关可用API端点的更多信息以及如何调用它们,请参阅API参考。

对于那些试图找到替代方案的人,我将Hazelcast用作分布式事件听众。在GitHub上添加了类似的POC:https://github.com/vinrar/hazelcastaseventlistener

我通过使用此脚本解决了此问题。您只需要编写等效命令即可进行API调用。我用 curl做到了。

以下是脚本的用法:

function usage {
    echo "usage: $PROGNAME [-n NAMESPACE] [-m MAX-PODS] -s SERVICE -- COMMAND"
    echo "  -s SERVICE   K8s service, i.e. a pod selector (required)"
    echo "     COMMAND   Command to execute on the pods"
    echo "  -n NAMESPACE K8s namespace (optional)"
    echo "  -m MAX-PODS  Max number of pods to run on (optional; default=all)"
    echo "  -q           Quiet mode"
    echo "  -d           Dry run (don't actually exec)"
}

例如,在使用名称s1和名称空间n1的服务的所有吊舱上运行命令curl http://google.com,您需要执行./kcdo -s s1 -n n1 -- curl http://google.com

我需要访问所有POD,以便可以更改类上的日志级别,因此我从一个吊舱的内部进行了:

// Change level to DEBUG
host <service-name>| awk '{print $4}' | while read line; do
curl --location --request POST "http://$line:9111/actuator/loggers/com.foo.MyClassName" 
--header 'Content-Type: application/json' 
--data-raw '{"configuredLevel": "DEBUG"}' 
done
// Query level on all pods
host <service-name>| awk '{print $4}' | while read line; do    
curl --location --request GET "http://$line:9111/actuator/loggers/com.foo.MyClassName"
echo
done

您需要hostcurl执行它。

不确定这是否是好习惯。

相关内容

  • 没有找到相关文章

最新更新