如何通过 kubectl 代理访问此 Kubernetes 服务?
How do I access this Kubernetes service via kubectl proxy?
我想通过 kubectl proxy server, but for some reason it won't work even though I can make it work for other services. Given the below service definition, why is it not available on http://localhost:8001/api/v1/proxy/namespaces/monitoring/services/grafana?
访问我的 Grafana Kubernetes 服务
grafana-service.yaml
apiVersion: v1
kind: Service
metadata:
namespace: monitoring
name: grafana
labels:
app: grafana
spec:
type: NodePort
ports:
- name: web
port: 3000
protocol: TCP
nodePort: 30902
selector:
app: grafana
grafana-deployment.yaml
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
namespace: monitoring
name: grafana
spec:
replicas: 1
template:
metadata:
labels:
app: grafana
spec:
containers:
- name: grafana
image: grafana/grafana:4.1.1
env:
- name: GF_AUTH_BASIC_ENABLED
value: "true"
- name: GF_AUTH_ANONYMOUS_ENABLED
value: "true"
- name: GF_SECURITY_ADMIN_USER
valueFrom:
secretKeyRef:
name: grafana-credentials
key: user
- name: GF_SECURITY_ADMIN_PASSWORD
valueFrom:
secretKeyRef:
name: grafana-credentials
key: password
volumeMounts:
- name: grafana-storage
mountPath: /var/grafana-storage
ports:
- name: web
containerPort: 3000
resources:
requests:
memory: 100Mi
cpu: 100m
limits:
memory: 200Mi
cpu: 200m
- name: grafana-watcher
image: quay.io/coreos/grafana-watcher:v0.0.5
args:
- '--watch-dir=/var/grafana-dashboards'
- '--grafana-url=http://localhost:3000'
env:
- name: GRAFANA_USER
valueFrom:
secretKeyRef:
name: grafana-credentials
key: user
- name: GRAFANA_PASSWORD
valueFrom:
secretKeyRef:
name: grafana-credentials
key: password
resources:
requests:
memory: "16Mi"
cpu: "50m"
limits:
memory: "32Mi"
cpu: "100m"
volumeMounts:
- name: grafana-dashboards
mountPath: /var/grafana-dashboards
volumes:
- name: grafana-storage
emptyDir: {}
- name: grafana-dashboards
configMap:
name: grafana-dashboards
我在访问上述 URL 时看到的错误是 "no endpoints available for service "grafana""",错误代码 503。
您的 Deployment 可能没有标签 app: grafana,或者不在另一个命名空间中。您还可以 post 部署定义吗?
有几个因素可能会导致此问题。
服务希望找到一个或多个支持端点,它通过标签上的匹配规则发现这些端点。如果标签不对齐,则服务将找不到端点,服务执行的网络网关功能将导致 503。
POD 声明的端口和容器内的进程与服务期望的 --target-port
不一致。
其中任何一个都可能产生错误。让我们仔细看看。
首先,kubectl describe
服务:
$ kubectl describe svc grafana01-grafana-3000
Name: grafana01-grafana-3000
Namespace: default
Labels: app=grafana01-grafana
chart=grafana-0.3.7
component=grafana
heritage=Tiller
release=grafana01
Annotations: <none>
Selector: app=grafana01-grafana,component=grafana,release=grafana01
Type: NodePort
IP: 10.0.0.197
Port: <unset> 3000/TCP
NodePort: <unset> 30905/TCP
Endpoints: 10.1.45.69:3000
Session Affinity: None
Events: <none>
请注意,我的 grafana 服务列出了 1 个端点(可能有多个)。您的示例中上面的错误表明您不会在此处列出端点。
Endpoints: 10.1.45.69:3000
接下来让我们看一下选择器。在上面的示例中,您可以看到我的服务上有 3 个选择器标签:
Selector: app=grafana01-grafana,component=grafana,release=grafana01
我会 kubectl describe
我的 pods 接下来:
$ kubectl describe pod grafana
Name: grafana01-grafana-1843344063-vp30d
Namespace: default
Node: 10.10.25.220/10.10.25.220
Start Time: Fri, 14 Jul 2017 03:25:11 +0000
Labels: app=grafana01-grafana
component=grafana
pod-template-hash=1843344063
release=grafana01
...
请注意 pod
上的标签正确对齐,因此我的服务发现 pods
提供 endpoints
,service
对其进行负载平衡。确认链的这一部分在您的环境中没有中断。
如果您确实发现标签是正确的,您可能仍然会断开连接,因为 pod
中的 container
中的 grafana 进程 运行 是 运行 在与您预期不同的端口上。
$ kubectl describe pod grafana
Name: grafana01-grafana-1843344063-vp30d
...
Containers:
grafana:
Container ID: docker://69f11b7828c01c5c3b395c008d88e8640c5606f4d865107bf4b433628cc36c76
Image: grafana/grafana:latest
Image ID: docker-pullable://grafana/grafana@sha256:11690015c430f2b08955e28c0e8ce7ce1c5883edfc521b68f3fb288e85578d26
Port: 3000/TCP
State: Running
Started: Fri, 14 Jul 2017 03:25:26 +0000
如果由于某种原因,容器下的 port
列出了不同的值,则该服务有效地针对无效端点进行了负载平衡。
例如,如果列出端口 80:
端口:80/TCP
或者是一个空值
端口:
那么即使您的标签选择器是正确的,该服务也永远不会找到来自 pod 的有效响应,并且会从轮换中删除端点。
我怀疑你的问题是上面的第一个问题(标签选择器不匹配)。
如果标签选择器和端口都对齐,则节点之间的 MTU 设置可能有问题。在某些情况下,如果您的网络层(如 calico)使用的 MTU 大于支持网络的 MTU,那么您将永远无法从端点获得有效响应。通常,最后一个潜在问题将表现为超时而不是 503。
正如迈克尔所说,很可能您的标签或命名空间不匹配。但是除此之外,请记住,即使您修复了端点,您之后的 url (http://localhost:8001/api/v1/proxy/namespaces/monitoring/services/grafana) 也可能无法正常工作。
根据您的 root_url and/or static_root_path grafana 配置设置,当您尝试登录时,您可能会看到 grafana trying to POST to http://localhost:8001/login 并获得404.
尝试改用 kubectl 端口转发:
kubectl -n monitoring port-forward [grafana-pod-name] 3000
访问grafana
https://kubernetes.io/docs/tasks/access-application-cluster/port-forward-access-application-cluster/
问题是 Grafana 的端口名为 web,因此需要将 :web
附加到 kubectl 代理 URL:http://localhost:8001/api/v1/proxy/namespaces/monitoring/services/grafana:web.
另一种方法是不命名 Grafana 端口,因为这样您就不必将 :web
附加到服务的 kubectl 代理 URL:http://localhost:8001/api/v1/proxy/namespaces/monitoring/services/grafana:web。我最后选择了这个选项,因为它更容易。
对于 Kubernetes 1.10,代理 URL 应该略有不同,如下所示:
http://localhost:8080/api/v1/namespaces/default/services/SERVICE-NAME:PORT-NAME/proxy/
我想通过 kubectl proxy server, but for some reason it won't work even though I can make it work for other services. Given the below service definition, why is it not available on http://localhost:8001/api/v1/proxy/namespaces/monitoring/services/grafana?
访问我的 Grafana Kubernetes 服务grafana-service.yaml
apiVersion: v1
kind: Service
metadata:
namespace: monitoring
name: grafana
labels:
app: grafana
spec:
type: NodePort
ports:
- name: web
port: 3000
protocol: TCP
nodePort: 30902
selector:
app: grafana
grafana-deployment.yaml
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
namespace: monitoring
name: grafana
spec:
replicas: 1
template:
metadata:
labels:
app: grafana
spec:
containers:
- name: grafana
image: grafana/grafana:4.1.1
env:
- name: GF_AUTH_BASIC_ENABLED
value: "true"
- name: GF_AUTH_ANONYMOUS_ENABLED
value: "true"
- name: GF_SECURITY_ADMIN_USER
valueFrom:
secretKeyRef:
name: grafana-credentials
key: user
- name: GF_SECURITY_ADMIN_PASSWORD
valueFrom:
secretKeyRef:
name: grafana-credentials
key: password
volumeMounts:
- name: grafana-storage
mountPath: /var/grafana-storage
ports:
- name: web
containerPort: 3000
resources:
requests:
memory: 100Mi
cpu: 100m
limits:
memory: 200Mi
cpu: 200m
- name: grafana-watcher
image: quay.io/coreos/grafana-watcher:v0.0.5
args:
- '--watch-dir=/var/grafana-dashboards'
- '--grafana-url=http://localhost:3000'
env:
- name: GRAFANA_USER
valueFrom:
secretKeyRef:
name: grafana-credentials
key: user
- name: GRAFANA_PASSWORD
valueFrom:
secretKeyRef:
name: grafana-credentials
key: password
resources:
requests:
memory: "16Mi"
cpu: "50m"
limits:
memory: "32Mi"
cpu: "100m"
volumeMounts:
- name: grafana-dashboards
mountPath: /var/grafana-dashboards
volumes:
- name: grafana-storage
emptyDir: {}
- name: grafana-dashboards
configMap:
name: grafana-dashboards
我在访问上述 URL 时看到的错误是 "no endpoints available for service "grafana""",错误代码 503。
您的 Deployment 可能没有标签 app: grafana,或者不在另一个命名空间中。您还可以 post 部署定义吗?
有几个因素可能会导致此问题。
服务希望找到一个或多个支持端点,它通过标签上的匹配规则发现这些端点。如果标签不对齐,则服务将找不到端点,服务执行的网络网关功能将导致 503。
POD 声明的端口和容器内的进程与服务期望的
--target-port
不一致。
其中任何一个都可能产生错误。让我们仔细看看。
首先,kubectl describe
服务:
$ kubectl describe svc grafana01-grafana-3000
Name: grafana01-grafana-3000
Namespace: default
Labels: app=grafana01-grafana
chart=grafana-0.3.7
component=grafana
heritage=Tiller
release=grafana01
Annotations: <none>
Selector: app=grafana01-grafana,component=grafana,release=grafana01
Type: NodePort
IP: 10.0.0.197
Port: <unset> 3000/TCP
NodePort: <unset> 30905/TCP
Endpoints: 10.1.45.69:3000
Session Affinity: None
Events: <none>
请注意,我的 grafana 服务列出了 1 个端点(可能有多个)。您的示例中上面的错误表明您不会在此处列出端点。
Endpoints: 10.1.45.69:3000
接下来让我们看一下选择器。在上面的示例中,您可以看到我的服务上有 3 个选择器标签:
Selector: app=grafana01-grafana,component=grafana,release=grafana01
我会 kubectl describe
我的 pods 接下来:
$ kubectl describe pod grafana
Name: grafana01-grafana-1843344063-vp30d
Namespace: default
Node: 10.10.25.220/10.10.25.220
Start Time: Fri, 14 Jul 2017 03:25:11 +0000
Labels: app=grafana01-grafana
component=grafana
pod-template-hash=1843344063
release=grafana01
...
请注意 pod
上的标签正确对齐,因此我的服务发现 pods
提供 endpoints
,service
对其进行负载平衡。确认链的这一部分在您的环境中没有中断。
如果您确实发现标签是正确的,您可能仍然会断开连接,因为 pod
中的 container
中的 grafana 进程 运行 是 运行 在与您预期不同的端口上。
$ kubectl describe pod grafana
Name: grafana01-grafana-1843344063-vp30d
...
Containers:
grafana:
Container ID: docker://69f11b7828c01c5c3b395c008d88e8640c5606f4d865107bf4b433628cc36c76
Image: grafana/grafana:latest
Image ID: docker-pullable://grafana/grafana@sha256:11690015c430f2b08955e28c0e8ce7ce1c5883edfc521b68f3fb288e85578d26
Port: 3000/TCP
State: Running
Started: Fri, 14 Jul 2017 03:25:26 +0000
如果由于某种原因,容器下的 port
列出了不同的值,则该服务有效地针对无效端点进行了负载平衡。
例如,如果列出端口 80: 端口:80/TCP 或者是一个空值 端口:
那么即使您的标签选择器是正确的,该服务也永远不会找到来自 pod 的有效响应,并且会从轮换中删除端点。
我怀疑你的问题是上面的第一个问题(标签选择器不匹配)。
如果标签选择器和端口都对齐,则节点之间的 MTU 设置可能有问题。在某些情况下,如果您的网络层(如 calico)使用的 MTU 大于支持网络的 MTU,那么您将永远无法从端点获得有效响应。通常,最后一个潜在问题将表现为超时而不是 503。
正如迈克尔所说,很可能您的标签或命名空间不匹配。但是除此之外,请记住,即使您修复了端点,您之后的 url (http://localhost:8001/api/v1/proxy/namespaces/monitoring/services/grafana) 也可能无法正常工作。
根据您的 root_url and/or static_root_path grafana 配置设置,当您尝试登录时,您可能会看到 grafana trying to POST to http://localhost:8001/login 并获得404.
尝试改用 kubectl 端口转发:
kubectl -n monitoring port-forward [grafana-pod-name] 3000
https://kubernetes.io/docs/tasks/access-application-cluster/port-forward-access-application-cluster/
问题是 Grafana 的端口名为 web,因此需要将 :web
附加到 kubectl 代理 URL:http://localhost:8001/api/v1/proxy/namespaces/monitoring/services/grafana:web.
另一种方法是不命名 Grafana 端口,因为这样您就不必将 :web
附加到服务的 kubectl 代理 URL:http://localhost:8001/api/v1/proxy/namespaces/monitoring/services/grafana:web。我最后选择了这个选项,因为它更容易。
对于 Kubernetes 1.10,代理 URL 应该略有不同,如下所示:
http://localhost:8080/api/v1/namespaces/default/services/SERVICE-NAME:PORT-NAME/proxy/