如何在运行时从 Go 代码获取 pod 外部 IP
How can I get pod external IP from Go code at runtime
很简单的问题,如何获取当前 go 代码为 运行 的 Pod?
我需要它,因为出于某种原因,我需要直接 ping Pod 的代码,而不是使用我的常规端点(负载均衡器)。
我当前的配置:
apiVersion: v1
kind: Service
metadata:
name: web-socket-service-api
spec:
ports:
# Port that accepts gRPC and JSON/HTTP2 requests over HTTP.
- port: 8080
targetPort: 8080
protocol: TCP
name: grpc
# Port that accepts gRPC and JSON/HTTP2 requests over HTTP.
- port: 8081
targetPort: 8081
protocol: TCP
name: rest
# Port that accepts WebSockets.
- port: 8082
targetPort: 8082
protocol: TCP
name: websocket
selector:
app: web-socket-service-api
type: LoadBalancer
---
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: web-socket-service-api
spec:
replicas: 3
template:
metadata:
labels:
app: web-socket-service-api
spec:
containers:
- name: web-socket-service-api
image: gcr.io/[PROJECT]/web-socket-service-api:latest
ports:
- containerPort: 8080
- containerPort: 8081
- containerPort: 8082
我试过了
/*
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
*/
func GetContainerIP() string {
// creates the in-cluster config
config, err := rest.InClusterConfig()
if err != nil {
panic(err.Error())
}
// creates the clientset
clientset, err := kubernetes.NewForConfig(config)
if err != nil {
panic(err.Error())
}
log.Println("checking pods")
pods, err := clientset.CoreV1().Pods("default").List(metav1.ListOptions{})
if err != nil {
panic(err.Error())
}
b, _ := json.Marshal(pods)
log.Println(string(b))
for _, pod := range pods.Items {
log.Println(pod.Name, pod.Status)
pod, err := clientset.CoreV1().Pods("default").Get(pod.Name, metav1.GetOptions{})
if err != nil {
panic(err.Error())
}
log.Println(pod.Status)
}
log.Println("checked pods")
return ""
}
但遗憾的是我得到了
panic: pods is forbidden: User "system:serviceaccount:default:default" cannot list resource "pods" in API group "" in the namespace "default"
而且我找不到修复它的方法或任何关于它的教程..
执行此操作的命令是 $ kubectl describe pods
从那里您将能够看到所有 pods 的所有详细信息。如果您知道您想要详细信息的特定 pod,只需在命令 ex 的末尾添加一个标签名称即可; $ kubectl 描述 pods 。有关 kubectl 命令的完整列表,请查看此 link
要使应用能够 API 调用 kubernetes 资源,应用需要必要的 RBAC 权限。最佳做法是创建 "pods" 的 "Read-only" 角色并将其与新的服务帐户绑定。
您可以在 here
中找到所有详细信息
片刻后我找到了答案,但完全忘了 post 在这里!
Please note that it will crash if you ain't in a Kubernetes env
import (
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
"os"
"os/signal"
"time"
)
//
// Pod infos
//
func GetPodDetails() (IP string, name string) {
// creates the in-cluster config
config, err := rest.InClusterConfig()
if err != nil {
panic(err.Error())
}
// creates the clientset
clientset, err := kubernetes.NewForConfig(config)
if err != nil {
panic(err.Error())
}
IP = ""
for {
if IP != "" {
break
} else {
log.Printf("No IP for now.\n")
}
pods, err := clientset.CoreV1().Pods("default").List(metav1.ListOptions{})
if err != nil {
panic(err.Error())
}
for _, pod := range pods.Items {
pod, _ := clientset.CoreV1().Pods("default").Get(pod.Name, metav1.GetOptions{})
if pod.Name == os.Getenv("HOSTNAME") {
IP = pod.Status.PodIP
}
}
log.Printf("Waits...\n")
time.Sleep(1 * time.Second)
}
name = os.Getenv("HOSTNAME")
log.Printf("Trying os.Getenv(\"HOSTNAME/IP\"): [%s][%s]\n", name, IP)
return IP, name
}
pod, err := clientset.CoreV1().Pods("default").Get(context.TODO(), os.Getenv("HOSTNAME"), metav1.GetOptions{})
podName := pod.Name
podIP := pod.Status.PodIP
node := pod.Spec.NodeName
很简单的问题,如何获取当前 go 代码为 运行 的 Pod?
我需要它,因为出于某种原因,我需要直接 ping Pod 的代码,而不是使用我的常规端点(负载均衡器)。
我当前的配置:
apiVersion: v1
kind: Service
metadata:
name: web-socket-service-api
spec:
ports:
# Port that accepts gRPC and JSON/HTTP2 requests over HTTP.
- port: 8080
targetPort: 8080
protocol: TCP
name: grpc
# Port that accepts gRPC and JSON/HTTP2 requests over HTTP.
- port: 8081
targetPort: 8081
protocol: TCP
name: rest
# Port that accepts WebSockets.
- port: 8082
targetPort: 8082
protocol: TCP
name: websocket
selector:
app: web-socket-service-api
type: LoadBalancer
---
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: web-socket-service-api
spec:
replicas: 3
template:
metadata:
labels:
app: web-socket-service-api
spec:
containers:
- name: web-socket-service-api
image: gcr.io/[PROJECT]/web-socket-service-api:latest
ports:
- containerPort: 8080
- containerPort: 8081
- containerPort: 8082
我试过了
/*
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
*/
func GetContainerIP() string {
// creates the in-cluster config
config, err := rest.InClusterConfig()
if err != nil {
panic(err.Error())
}
// creates the clientset
clientset, err := kubernetes.NewForConfig(config)
if err != nil {
panic(err.Error())
}
log.Println("checking pods")
pods, err := clientset.CoreV1().Pods("default").List(metav1.ListOptions{})
if err != nil {
panic(err.Error())
}
b, _ := json.Marshal(pods)
log.Println(string(b))
for _, pod := range pods.Items {
log.Println(pod.Name, pod.Status)
pod, err := clientset.CoreV1().Pods("default").Get(pod.Name, metav1.GetOptions{})
if err != nil {
panic(err.Error())
}
log.Println(pod.Status)
}
log.Println("checked pods")
return ""
}
但遗憾的是我得到了
panic: pods is forbidden: User "system:serviceaccount:default:default" cannot list resource "pods" in API group "" in the namespace "default"
而且我找不到修复它的方法或任何关于它的教程..
执行此操作的命令是 $ kubectl describe pods 从那里您将能够看到所有 pods 的所有详细信息。如果您知道您想要详细信息的特定 pod,只需在命令 ex 的末尾添加一个标签名称即可; $ kubectl 描述 pods 。有关 kubectl 命令的完整列表,请查看此 link
要使应用能够 API 调用 kubernetes 资源,应用需要必要的 RBAC 权限。最佳做法是创建 "pods" 的 "Read-only" 角色并将其与新的服务帐户绑定。
您可以在 here
中找到所有详细信息片刻后我找到了答案,但完全忘了 post 在这里!
Please note that it will crash if you ain't in a Kubernetes env
import (
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
"os"
"os/signal"
"time"
)
//
// Pod infos
//
func GetPodDetails() (IP string, name string) {
// creates the in-cluster config
config, err := rest.InClusterConfig()
if err != nil {
panic(err.Error())
}
// creates the clientset
clientset, err := kubernetes.NewForConfig(config)
if err != nil {
panic(err.Error())
}
IP = ""
for {
if IP != "" {
break
} else {
log.Printf("No IP for now.\n")
}
pods, err := clientset.CoreV1().Pods("default").List(metav1.ListOptions{})
if err != nil {
panic(err.Error())
}
for _, pod := range pods.Items {
pod, _ := clientset.CoreV1().Pods("default").Get(pod.Name, metav1.GetOptions{})
if pod.Name == os.Getenv("HOSTNAME") {
IP = pod.Status.PodIP
}
}
log.Printf("Waits...\n")
time.Sleep(1 * time.Second)
}
name = os.Getenv("HOSTNAME")
log.Printf("Trying os.Getenv(\"HOSTNAME/IP\"): [%s][%s]\n", name, IP)
return IP, name
}
pod, err := clientset.CoreV1().Pods("default").Get(context.TODO(), os.Getenv("HOSTNAME"), metav1.GetOptions{})
podName := pod.Name
podIP := pod.Status.PodIP
node := pod.Spec.NodeName