Switch language name 'zh' to 'zh-cn'
This is the first step to rename 'zh' to 'zh-cn'. There are several reasons why we rename the language name.
- The upstream docsy theme changed the language name, leading to many warnings during site build;
The side-effect is that the i18n strings are no longer working.
- We believe renaming the language is the right thing to do, because this move can make room for other variants of Chinese language, such as 'zh-tw', 'zh-sg' etc.
There would be several follow-ups to this PR, such as fixing the intra-site links, adding redirects etc.
We will lock up changes to zh/zh-cn pages for the moment, until this one gets in.
This PR is based on commit cdad0a7342.
This commit is contained in:
@@ -0,0 +1,220 @@
|
||||
---
|
||||
title: 监控、日志和调试
|
||||
description: 设置监控和日志记录以对集群进行故障排除或调试容器化应用程序。
|
||||
weight: 20
|
||||
content_type: concept
|
||||
no_list: true
|
||||
---
|
||||
<!--
|
||||
title: "Monitoring, Logging, and Debugging"
|
||||
description: Set up monitoring and logging to troubleshoot a cluster, or debug a containerized application.
|
||||
weight: 20
|
||||
reviewers:
|
||||
- brendandburns
|
||||
- davidopp
|
||||
content_type: concept
|
||||
no_list: true
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
<!--
|
||||
Sometimes things go wrong. This guide is aimed at making them right. It has
|
||||
two sections:
|
||||
-->
|
||||
有时候事情会出错。本指南旨在解决这些问题。它包含两个部分:
|
||||
|
||||
<!--
|
||||
* [Debugging your application](/docs/tasks/debug/debug-application/) - Useful
|
||||
for users who are deploying code into Kubernetes and wondering why it is not working.
|
||||
* [Debugging your cluster](/docs/tasks/debug/debug-cluster/) - Useful
|
||||
for cluster administrators and people whose Kubernetes cluster is unhappy.
|
||||
-->
|
||||
* [应用排错](/zh/docs/tasks/debug/debug-application/) -
|
||||
针对部署代码到 Kubernetes 并想知道代码为什么不能正常运行的用户。
|
||||
* [集群排错](/zh/docs/tasks/debug/debug-cluster/) -
|
||||
针对集群管理员以及 Kubernetes 集群表现异常的用户。
|
||||
|
||||
<!--
|
||||
You should also check the known issues for the [release](https://github.com/kubernetes/kubernetes/releases)
|
||||
you're using.
|
||||
-->
|
||||
你也应该查看所用[发行版本](https://github.com/kubernetes/kubernetes/releases)的已知问题。
|
||||
|
||||
<!-- body -->
|
||||
|
||||
<!--
|
||||
## Getting help
|
||||
|
||||
If your problem isn't answered by any of the guides above, there are variety of
|
||||
ways for you to get help from the Kubernetes team.
|
||||
-->
|
||||
## 获取帮助 {#getting-help}
|
||||
|
||||
如果你的问题在上述指南中没有得到答案,你还有另外几种方式从 Kubernetes 团队获得帮助。
|
||||
|
||||
<!--
|
||||
### Questions
|
||||
|
||||
The documentation on this site has been structured to provide answers to a wide
|
||||
range of questions. [Concepts](/docs/concepts/) explain the Kubernetes
|
||||
architecture and how each component works, while [Setup](/docs/setup/) provides
|
||||
practical instructions for getting started. [Tasks](/docs/tasks/) show how to
|
||||
accomplish commonly used tasks, and [Tutorials](/docs/tutorials/) are more
|
||||
comprehensive walkthroughs of real-world, industry-specific, or end-to-end
|
||||
development scenarios. The [Reference](/docs/reference/) section provides
|
||||
detailed documentation on the [Kubernetes API](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/)
|
||||
and command-line interfaces (CLIs), such as [`kubectl`](/docs/reference/kubectl/).
|
||||
-->
|
||||
### 问题 {#questions}
|
||||
|
||||
本网站上的文档针对回答各类问题进行了结构化组织和分类。
|
||||
[概念](/zh/docs/concepts/)部分解释 Kubernetes 体系结构以及每个组件的工作方式,
|
||||
[安装](/zh/docs/setup/)部分提供了安装的实用说明。
|
||||
[任务](/zh/docs/tasks/)部分展示了如何完成常用任务,
|
||||
[教程](/zh/docs/tutorials/)部分则提供对现实世界、特定行业或端到端开发场景的更全面的演练。
|
||||
[参考](/zh/docs/reference/)部分提供了详细的
|
||||
[Kubernetes API](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/) 文档
|
||||
和命令行 (CLI) 接口的文档,例如[`kubectl`](/zh/docs/reference/kubectl/)。
|
||||
|
||||
<!--
|
||||
## Help! My question isn't covered! I need help now!
|
||||
-->
|
||||
## 求救!我的问题还没有解决!我现在需要帮助!
|
||||
|
||||
<!--
|
||||
### Stack Overflow
|
||||
|
||||
Someone else from the community may have already asked a similar question or may
|
||||
be able to help with your problem. The Kubernetes team will also monitor
|
||||
[posts tagged Kubernetes](https://stackoverflow.com/questions/tagged/kubernetes).
|
||||
If there aren't any existing questions that help, **please [ensure that your question is on-topic on Stack Overflow](https://stackoverflow.com/help/on-topic)
|
||||
and that you read through the guidance on [how to ask a new question](https://stackoverflow.com/help/how-to-ask)**,
|
||||
before [asking a new one](https://stackoverflow.com/questions/ask?tags=kubernetes)!
|
||||
-->
|
||||
### Stack Overflow {#stack-overflow}
|
||||
|
||||
社区中的其他人可能已经问过和你类似的问题,也可能能够帮助解决你的问题。
|
||||
Kubernetes 团队还会监视[带有 Kubernetes 标签的帖子](https://stackoverflow.com/questions/tagged/kubernetes)。
|
||||
如果现有的问题对你没有帮助,在[问一个新问题](https://stackoverflow.com/questions/ask?tags=kubernetes)
|
||||
之前,**请[确保你的问题是关于 Stack Overflow 的主题](https://stackoverflow.com/help/on-topic)
|
||||
并且你需要阅读关于[如何提出新问题](https://stackoverflow.com/help/how-to-ask)
|
||||
的指南。**
|
||||
|
||||
<!--
|
||||
### Slack
|
||||
|
||||
Many people from the Kubernetes community hang out on Kubernetes Slack in the `#kubernetes-users` channel.
|
||||
Slack requires registration; you can [request an invitation](https://slack.kubernetes.io),
|
||||
and registration is open to everyone). Feel free to come and ask any and all questions.
|
||||
Once registered, access the [Kubernetes organisation in Slack](https://kubernetes.slack.com)
|
||||
via your web browser or via Slack's own dedicated app.
|
||||
-->
|
||||
### Slack
|
||||
|
||||
Kubernetes 社区中有很多人在 `#kubernetes-users` 这一 Slack 频道聚集。
|
||||
Slack 需要注册;你可以[请求一份邀请](https://slack.kubernetes.io),
|
||||
并且注册是对所有人开放的。欢迎你随时来问任何问题。
|
||||
一旦注册了,就可以访问通过 Web 浏览器或者 Slack 专用的应用访问
|
||||
[Slack 上的 Kubernetes 组织](https://kubernetes.slack.com)。
|
||||
|
||||
<!--
|
||||
Once you are registered, browse the growing list of channels for various subjects of
|
||||
interest. For example, people new to Kubernetes may also want to join the
|
||||
[`#kubernetes-novice`](https://kubernetes.slack.com/messages/kubernetes-novice) channel. As another example, developers should join the
|
||||
[`#kubernetes-dev`](https://kubernetes.slack.com/messages/kubernetes-dev) channel.
|
||||
-->
|
||||
一旦你完成了注册,就可以浏览各种感兴趣主题的频道列表(一直在增长)。
|
||||
例如,Kubernetes 新人可能还想加入
|
||||
[`#kubernetes-novice`](https://kubernetes.slack.com/messages/kubernetes-novice)
|
||||
频道。又比如,开发人员应该加入
|
||||
[`#kubernetes-dev`](https://kubernetes.slack.com/messages/kubernetes-dev)
|
||||
频道。
|
||||
|
||||
<!--
|
||||
There are also many country specific/local language channels. Feel free to join
|
||||
these channels for localized support and info:
|
||||
-->
|
||||
还有许多国家/地区语言频道。请随时加入这些频道以获得本地化支持和信息:
|
||||
|
||||
{{< table caption="Country / language specific Slack channels" >}}
|
||||
<!--
|
||||
Country | Channels
|
||||
:---------|:------------
|
||||
China | [`#cn-users`](https://kubernetes.slack.com/messages/cn-users), [`#cn-events`](https://kubernetes.slack.com/messages/cn-events)
|
||||
Finland | [`#fi-users`](https://kubernetes.slack.com/messages/fi-users)
|
||||
France | [`#fr-users`](https://kubernetes.slack.com/messages/fr-users), [`#fr-events`](https://kubernetes.slack.com/messages/fr-events)
|
||||
Germany | [`#de-users`](https://kubernetes.slack.com/messages/de-users), [`#de-events`](https://kubernetes.slack.com/messages/de-events)
|
||||
India | [`#in-users`](https://kubernetes.slack.com/messages/in-users), [`#in-events`](https://kubernetes.slack.com/messages/in-events)
|
||||
Italy | [`#it-users`](https://kubernetes.slack.com/messages/it-users), [`#it-events`](https://kubernetes.slack.com/messages/it-events)
|
||||
Japan | [`#jp-users`](https://kubernetes.slack.com/messages/jp-users), [`#jp-events`](https://kubernetes.slack.com/messages/jp-events)
|
||||
Korea | [`#kr-users`](https://kubernetes.slack.com/messages/kr-users)
|
||||
Netherlands | [`#nl-users`](https://kubernetes.slack.com/messages/nl-users)
|
||||
Norway | [`#norw-users`](https://kubernetes.slack.com/messages/norw-users)
|
||||
Poland | [`#pl-users`](https://kubernetes.slack.com/messages/pl-users)
|
||||
Russia | [`#ru-users`](https://kubernetes.slack.com/messages/ru-users)
|
||||
Spain | [`#es-users`](https://kubernetes.slack.com/messages/es-users)
|
||||
Sweden | [`#se-users`](https://kubernetes.slack.com/messages/se-users)
|
||||
Turkey | [`#tr-users`](https://kubernetes.slack.com/messages/tr-users), [`#tr-events`](https://kubernetes.slack.com/messages/tr-events)
|
||||
-->
|
||||
国家 | 频道
|
||||
:------|:------------
|
||||
中国 | [`#cn-users`](https://kubernetes.slack.com/messages/cn-users), [`#cn-events`](https://kubernetes.slack.com/messages/cn-events)
|
||||
芬兰 | [`#fi-users`](https://kubernetes.slack.com/messages/fi-users)
|
||||
法国 | [`#fr-users`](https://kubernetes.slack.com/messages/fr-users), [`#fr-events`](https://kubernetes.slack.com/messages/fr-events)
|
||||
德国 | [`#de-users`](https://kubernetes.slack.com/messages/de-users), [`#de-events`](https://kubernetes.slack.com/messages/de-events)
|
||||
印度 | [`#in-users`](https://kubernetes.slack.com/messages/in-users), [`#in-events`](https://kubernetes.slack.com/messages/in-events)
|
||||
意大利 | [`#it-users`](https://kubernetes.slack.com/messages/it-users), [`#it-events`](https://kubernetes.slack.com/messages/it-events)
|
||||
日本 | [`#jp-users`](https://kubernetes.slack.com/messages/jp-users), [`#jp-events`](https://kubernetes.slack.com/messages/jp-events)
|
||||
韩国 | [`#kr-users`](https://kubernetes.slack.com/messages/kr-users)
|
||||
荷兰 | [`#nl-users`](https://kubernetes.slack.com/messages/nl-users)
|
||||
挪威 | [`#norw-users`](https://kubernetes.slack.com/messages/norw-users)
|
||||
波兰 | [`#pl-users`](https://kubernetes.slack.com/messages/pl-users)
|
||||
俄罗斯 | [`#ru-users`](https://kubernetes.slack.com/messages/ru-users)
|
||||
西班牙 | [`#es-users`](https://kubernetes.slack.com/messages/es-users)
|
||||
瑞典 | [`#se-users`](https://kubernetes.slack.com/messages/se-users)
|
||||
土耳其 | [`#tr-users`](https://kubernetes.slack.com/messages/tr-users), [`#tr-events`](https://kubernetes.slack.com/messages/tr-events)
|
||||
|
||||
{{< /table >}}
|
||||
|
||||
<!--
|
||||
### Forum
|
||||
|
||||
You're welcome to join the official Kubernetes Forum: [discuss.kubernetes.io](https://discuss.kubernetes.io).
|
||||
-->
|
||||
### 论坛 {#forum}
|
||||
|
||||
欢迎你加入 Kubernetes 官方论坛
|
||||
[discuss.kubernetes.io](https://discuss.kubernetes.io)。
|
||||
|
||||
<!--
|
||||
### Bugs and Feature requests
|
||||
|
||||
If you have what looks like a bug, or you would like to make a feature request,
|
||||
please use the [Github issue tracking system](https://github.com/kubernetes/kubernetes/issues).
|
||||
-->
|
||||
### Bugs 和功能请求 {#bugs-and-feature-requests}
|
||||
|
||||
如果你发现一个看起来像 Bug 的问题,或者你想提出一个功能请求,请使用
|
||||
[Github 问题跟踪系统](https://github.com/kubernetes/kubernetes/issues)。
|
||||
|
||||
<!--
|
||||
Before you file an issue, please search existing issues to see if your issue is
|
||||
already covered.
|
||||
|
||||
If filing a bug, please include detailed information about how to reproduce the
|
||||
problem, such as:
|
||||
-->
|
||||
在提交问题之前,请搜索现有问题列表以查看是否其中已涵盖你的问题。
|
||||
|
||||
如果提交 Bug,请提供如何重现问题的详细信息,例如:
|
||||
|
||||
<!--
|
||||
* Kubernetes version: `kubectl version`
|
||||
* Cloud provider, OS distro, network configuration, and Docker version
|
||||
* Steps to reproduce the problem
|
||||
-->
|
||||
* Kubernetes 版本:`kubectl version`
|
||||
* 云平台、OS 发行版、网络配置和 Docker 版本
|
||||
* 重现问题的步骤
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
---
|
||||
title: "应用故障排除"
|
||||
description: 调试常见的容器应用问题.
|
||||
weight: 20
|
||||
---
|
||||
|
||||
<!--
|
||||
title: "Troubleshooting Applications"
|
||||
description: Debugging common containerized application issues.
|
||||
weight: 20
|
||||
-->
|
||||
|
||||
<!--
|
||||
This doc contains a set of resources for fixing issues with containerized applications. It covers things like common issues with Kubernetes resources (like Pods, Services, or StatefulSets), advice on making sense of container termination messages, and ways to debug running containers.
|
||||
-->
|
||||
该文档包含一组用于解决容器化应用程序问题的资源。
|
||||
它涵盖了诸如 Kubernetes 资源(如 Pod、Service 或 StatefulSets)的常见问题、
|
||||
关于理解容器终止消息的建议以及调试正在运行的容器的方法。
|
||||
@@ -0,0 +1,194 @@
|
||||
---
|
||||
title: 调试 Init 容器
|
||||
content_type: task
|
||||
weight: 40
|
||||
---
|
||||
|
||||
<!--
|
||||
reviewers:
|
||||
- bprashanth
|
||||
- enisoc
|
||||
- erictune
|
||||
- foxish
|
||||
- janetkuo
|
||||
- kow3ns
|
||||
- smarterclayton
|
||||
title: Debug Init Containers
|
||||
content_type: task
|
||||
weight: 40
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
<!--
|
||||
This page shows how to investigate problems related to the execution of
|
||||
Init Containers. The example command lines below refer to the Pod as
|
||||
`<pod-name>` and the Init Containers as `<init-container-1>` and
|
||||
`<init-container-2>`.
|
||||
-->
|
||||
此页显示如何核查与 Init 容器执行相关的问题。
|
||||
下面的示例命令行将 Pod 称为 `<pod-name>`,而 Init 容器称为 `<init-container-1>` 和
|
||||
`<init-container-2>`。
|
||||
|
||||
## {{% heading "prerequisites" %}}
|
||||
|
||||
{{< include "task-tutorial-prereqs.md" >}} {{< version-check >}}
|
||||
|
||||
<!--
|
||||
* You should be familiar with the basics of
|
||||
[Init Containers](/docs/concepts/workloads/pods/init-containers/).
|
||||
* You should have [Configured an Init Container](/docs/tasks/configure-pod-container/configure-pod-initialization/#creating-a-pod-that-has-an-init-container/).
|
||||
-->
|
||||
|
||||
* 你应该熟悉 [Init 容器](/zh/docs/concepts/workloads/pods/init-containers/)的基础知识。
|
||||
* 你应该已经[配置好一个 Init 容器](/zh/docs/tasks/configure-pod-container/configure-pod-initialization/#creating-a-pod-that-has-an-init-container/)。
|
||||
|
||||
<!-- steps -->
|
||||
|
||||
<!--
|
||||
## Checking the status of Init Containers
|
||||
|
||||
Display the status of your pod:
|
||||
-->
|
||||
|
||||
## 检查 Init 容器的状态
|
||||
|
||||
显示你的 Pod 的状态:
|
||||
|
||||
```shell
|
||||
kubectl get pod <pod-name>
|
||||
```
|
||||
|
||||
<!--
|
||||
For example, a status of `Init:1/2` indicates that one of two Init Containers
|
||||
has completed successfully:
|
||||
-->
|
||||
|
||||
例如,状态 `Init:1/2` 表明两个 Init 容器中的一个已经成功完成:
|
||||
|
||||
```
|
||||
NAME READY STATUS RESTARTS AGE
|
||||
<pod-name> 0/1 Init:1/2 0 7s
|
||||
```
|
||||
|
||||
<!--
|
||||
See [Understanding Pod status](#understanding-pod-status) for more examples of
|
||||
status values and their meanings.
|
||||
-->
|
||||
更多状态值及其含义请参考[理解 Pod 的状态](#understanding-pod-status)。
|
||||
|
||||
<!--
|
||||
## Getting details about Init Containers
|
||||
|
||||
View more detailed information about Init Container execution:
|
||||
-->
|
||||
## 获取 Init 容器详情 {#getting-details-about-init-containers}
|
||||
|
||||
查看 Init 容器运行的更多详情:
|
||||
|
||||
```shell
|
||||
kubectl describe pod <pod-name>
|
||||
```
|
||||
|
||||
<!--
|
||||
For example, a Pod with two Init Containers might show the following:
|
||||
-->
|
||||
例如,对于包含两个 Init 容器的 Pod 可能显示如下信息:
|
||||
|
||||
```
|
||||
Init Containers:
|
||||
<init-container-1>:
|
||||
Container ID: ...
|
||||
...
|
||||
State: Terminated
|
||||
Reason: Completed
|
||||
Exit Code: 0
|
||||
Started: ...
|
||||
Finished: ...
|
||||
Ready: True
|
||||
Restart Count: 0
|
||||
...
|
||||
<init-container-2>:
|
||||
Container ID: ...
|
||||
...
|
||||
State: Waiting
|
||||
Reason: CrashLoopBackOff
|
||||
Last State: Terminated
|
||||
Reason: Error
|
||||
Exit Code: 1
|
||||
Started: ...
|
||||
Finished: ...
|
||||
Ready: False
|
||||
Restart Count: 3
|
||||
...
|
||||
```
|
||||
|
||||
<!--
|
||||
You can also access the Init Container statuses programmatically by reading the
|
||||
`status.initContainerStatuses` field on the Pod Spec:
|
||||
-->
|
||||
你还可以通过编程方式读取 Pod Spec 上的 `status.initContainerStatuses` 字段,了解 Init 容器的状态:
|
||||
|
||||
```shell
|
||||
kubectl get pod nginx --template '{{.status.initContainerStatuses}}'
|
||||
```
|
||||
|
||||
<!--
|
||||
This command will return the same information as above in raw JSON.
|
||||
-->
|
||||
此命令将返回与原始 JSON 中相同的信息.
|
||||
|
||||
<!--
|
||||
## Accessing logs from Init Containers
|
||||
|
||||
Pass the Init Container name along with the Pod name
|
||||
to access its logs.
|
||||
-->
|
||||
## 通过 Init 容器访问日志 {#accessing-logs-from-init-containers}
|
||||
|
||||
与 Pod 名称一起传递 Init 容器名称,以访问容器的日志。
|
||||
|
||||
```shell
|
||||
kubectl logs <pod-name> -c <init-container-2>
|
||||
```
|
||||
|
||||
<!--
|
||||
Init Containers that run a shell script print
|
||||
commands as they're executed. For example, you can do this in Bash by running
|
||||
`set -x` at the beginning of the script.
|
||||
-->
|
||||
运行 Shell 脚本的 Init 容器在执行 Shell 脚本时输出命令本身。
|
||||
例如,你可以在 Bash 中通过在脚本的开头运行 `set -x` 来实现。
|
||||
|
||||
<!-- discussion -->
|
||||
|
||||
<!--
|
||||
## Understanding Pod status
|
||||
|
||||
A Pod status beginning with `Init:` summarizes the status of Init Container
|
||||
execution. The table below describes some example status values that you might
|
||||
see while debugging Init Containers.
|
||||
-->
|
||||
## 理解 Pod 的状态 {#understanding-pod-status}
|
||||
|
||||
以 `Init:` 开头的 Pod 状态汇总了 Init 容器执行的状态。
|
||||
下表介绍调试 Init 容器时可能看到的一些状态值示例。
|
||||
|
||||
<!--
|
||||
Status | Meaning
|
||||
------ | -------
|
||||
`Init:N/M` | The Pod has `M` Init Containers, and `N` have completed so far.
|
||||
`Init:Error` | An Init Container has failed to execute.
|
||||
`Init:CrashLoopBackOff` | An Init Container has failed repeatedly.
|
||||
`Pending` | The Pod has not yet begun executing Init Containers.
|
||||
`PodInitializing` or `Running` | The Pod has already finished executing Init Containers.
|
||||
-->
|
||||
|
||||
状态 | 含义
|
||||
------ | -------
|
||||
`Init:N/M` | Pod 包含 `M` 个 Init 容器,其中 `N` 个已经运行完成。
|
||||
`Init:Error` | Init 容器已执行失败。
|
||||
`Init:CrashLoopBackOff` | Init 容器执行总是失败。
|
||||
`Pending` | Pod 还没有开始执行 Init 容器。
|
||||
`PodInitializing` or `Running` | Pod 已经完成执行 Init 容器。
|
||||
|
||||
@@ -0,0 +1,305 @@
|
||||
---
|
||||
title: 调试 Pod
|
||||
content_type: concept
|
||||
weight: 10
|
||||
---
|
||||
|
||||
<!--
|
||||
reviewers:
|
||||
- mikedanese
|
||||
- thockin
|
||||
title: Debug Pods
|
||||
content_type: concept
|
||||
weight: 10
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
<!--
|
||||
This guide is to help users debug applications that are deployed into Kubernetes and not behaving correctly.
|
||||
This is *not* a guide for people who want to debug their cluster. For that you should check out
|
||||
[this guide](/docs/tasks/debug/debug-cluster).
|
||||
-->
|
||||
|
||||
本指南帮助用户调试那些部署到 Kubernetes 上后没有正常运行的应用。
|
||||
本指南 **并非** 指导用户如何调试集群。
|
||||
如果想调试集群的话,请参阅[这里](/zh/docs/tasks/debug/debug-cluster)。
|
||||
|
||||
|
||||
<!-- body -->
|
||||
|
||||
<!--
|
||||
## Diagnosing the problem
|
||||
|
||||
The first step in troubleshooting is triage. What is the problem? Is it your Pods, your Replication Controller or
|
||||
your Service?
|
||||
|
||||
* [Debugging Pods](#debugging-pods)
|
||||
* [Debugging Replication Controllers](#debugging-replication-controllers)
|
||||
* [Debugging Services](#debugging-services)
|
||||
-->
|
||||
## 诊断问题 {#diagnosing-the-problem}
|
||||
|
||||
故障排查的第一步是先给问题分类。问题是什么?是关于 Pod、Replication Controller 还是 Service?
|
||||
|
||||
* [调试 Pod](#debugging-pods)
|
||||
* [调试 Replication Controller](#debugging-replication-controllers)
|
||||
* [调试 Service](#debugging-services)
|
||||
|
||||
<!--
|
||||
### Debugging Pods
|
||||
|
||||
The first step in debugging a Pod is taking a look at it. Check the current state of the Pod and recent events with the following command:
|
||||
-->
|
||||
### 调试 Pod {#debugging-pods}
|
||||
|
||||
调试 Pod 的第一步是查看 Pod 信息。用如下命令查看 Pod 的当前状态和最近的事件:
|
||||
|
||||
```shell
|
||||
kubectl describe pods ${POD_NAME}
|
||||
```
|
||||
|
||||
<!--
|
||||
Look at the state of the containers in the pod. Are they all `Running`? Have there been recent restarts?
|
||||
|
||||
Continue debugging depending on the state of the pods.
|
||||
-->
|
||||
查看一下 Pod 中的容器所处的状态。这些容器的状态都是 `Running` 吗?最近有没有重启过?
|
||||
|
||||
后面的调试都是要依靠 Pod 的状态的。
|
||||
|
||||
<!--
|
||||
#### My pod stays pending
|
||||
|
||||
If a Pod is stuck in `Pending` it means that it can not be scheduled onto a node. Generally this is because
|
||||
there are insufficient resources of one type or another that prevent scheduling. Look at the output of the
|
||||
`kubectl describe ...` command above. There should be messages from the scheduler about why it can not schedule
|
||||
your pod. Reasons include:
|
||||
-->
|
||||
#### Pod 停滞在 Pending 状态
|
||||
|
||||
如果一个 Pod 停滞在 `Pending` 状态,表示 Pod 没有被调度到节点上。通常这是因为
|
||||
某种类型的资源不足导致无法调度。
|
||||
查看上面的 `kubectl describe ...` 命令的输出,其中应该显示了为什么没被调度的原因。
|
||||
常见原因如下:
|
||||
|
||||
<!--
|
||||
* **You don't have enough resources**: You may have exhausted the supply of CPU or Memory in your cluster, in this case
|
||||
you need to delete Pods, adjust resource requests, or add new nodes to your cluster. See
|
||||
[Compute Resources document](/docs/concepts/configuration/manage-resources-containers/) for more information.
|
||||
|
||||
* **You are using `hostPort`**: When you bind a Pod to a `hostPort` there are a limited number of places that pod can be
|
||||
scheduled. In most cases, `hostPort` is unnecessary, try using a Service object to expose your Pod. If you do require
|
||||
`hostPort` then you can only schedule as many Pods as there are nodes in your Kubernetes cluster.
|
||||
-->
|
||||
* **资源不足**:
|
||||
你可能耗尽了集群上所有的 CPU 或内存。此时,你需要删除 Pod、调整资源请求或者为集群添加节点。
|
||||
更多信息请参阅[计算资源文档](/zh/docs/concepts/configuration/manage-resources-containers/)
|
||||
|
||||
* **使用了 `hostPort`**:
|
||||
如果绑定 Pod 到 `hostPort`,那么能够运行该 Pod 的节点就有限了。
|
||||
多数情况下,`hostPort` 是非必要的,而应该采用 Service 对象来暴露 Pod。
|
||||
如果确实需要使用 `hostPort`,那么集群中节点的个数就是所能创建的 Pod
|
||||
的数量上限。
|
||||
|
||||
<!--
|
||||
#### My pod stays waiting
|
||||
|
||||
If a Pod is stuck in the `Waiting` state, then it has been scheduled to a worker node, but it can't run on that machine.
|
||||
Again, the information from `kubectl describe ...` should be informative. The most common cause of `Waiting` pods is a failure to pull the image. There are three things to check:
|
||||
|
||||
* Make sure that you have the name of the image correct.
|
||||
* Have you pushed the image to the registry?
|
||||
* Try to manually pull the image to see if the image can be pulled. For example,
|
||||
if you use Docker on your PC, run `docker pull <image>`.
|
||||
-->
|
||||
#### Pod 停滞在 Waiting 状态
|
||||
|
||||
如果 Pod 停滞在 `Waiting` 状态,则表示 Pod 已经被调度到某工作节点,但是无法在该节点上运行。
|
||||
同样,`kubectl describe ...` 命令的输出可能很有用。
|
||||
`Waiting` 状态的最常见原因是拉取镜像失败。要检查的有三个方面:
|
||||
|
||||
* 确保镜像名字拼写正确
|
||||
* 确保镜像已被推送到镜像仓库
|
||||
* 尝试手动是否能拉取镜像。例如,如果你在你的 PC 上使用 Docker,请运行 `docker pull <镜像>`。
|
||||
|
||||
<!--
|
||||
#### My pod is crashing or otherwise unhealthy
|
||||
|
||||
Once your pod has been scheduled, the methods described in [Debug Running Pods](
|
||||
/docs/tasks/debug/debug-application/debug-running-pod/) are available for debugging.
|
||||
-->
|
||||
#### Pod 处于 Crashing 或别的不健康状态
|
||||
|
||||
一旦 Pod 被调度,就可以采用
|
||||
[调试运行中的 Pod](/zh/docs/tasks/debug/debug-application/debug-running-pod/)
|
||||
中的方法来进一步调试。
|
||||
|
||||
<!--
|
||||
#### My pod is running but not doing what I told it to do
|
||||
|
||||
If your pod is not behaving as you expected, it may be that there was an error in your
|
||||
pod description (e.g. `mypod.yaml` file on your local machine), and that the error
|
||||
was silently ignored when you created the pod. Often a section of the pod description
|
||||
is nested incorrectly, or a key name is typed incorrectly, and so the key is ignored.
|
||||
For example, if you misspelled `command` as `commnd` then the pod will be created but
|
||||
will not use the command line you intended it to use.
|
||||
-->
|
||||
#### Pod 处于 Running 态但是没有正常工作
|
||||
|
||||
如果 Pod 行为不符合预期,很可能 Pod 描述(例如你本地机器上的 `mypod.yaml`)中有问题,
|
||||
并且该错误在创建 Pod 时被忽略掉,没有报错。
|
||||
通常,Pod 的定义中节区嵌套关系错误、字段名字拼错的情况都会引起对应内容被忽略掉。
|
||||
例如,如果你误将 `command` 写成 `commnd`,Pod 虽然可以创建,但它不会执行
|
||||
你期望它执行的命令行。
|
||||
|
||||
<!--
|
||||
The first thing to do is to delete your pod and try creating it again with the `--validate` option.
|
||||
For example, run `kubectl apply --validate -f mypod.yaml`.
|
||||
If you misspelled `command` as `commnd` then will give an error like this:
|
||||
-->
|
||||
可以做的第一件事是删除你的 Pod,并尝试带有 `--validate` 选项重新创建。
|
||||
例如,运行 `kubectl apply --validate -f mypod.yaml`。
|
||||
如果 `command` 被误拼成 `commnd`,你将会看到下面的错误信息:
|
||||
|
||||
```
|
||||
I0805 10:43:25.129850 46757 schema.go:126] unknown field: commnd
|
||||
I0805 10:43:25.129973 46757 schema.go:129] this may be a false alarm, see https://github.com/kubernetes/kubernetes/issues/6842
|
||||
pods/mypod
|
||||
```
|
||||
|
||||
<!-- TODO: Now that #11914 is merged, this advice may need to be updated -->
|
||||
|
||||
<!--
|
||||
The next thing to check is whether the pod on the apiserver
|
||||
matches the pod you meant to create (e.g. in a yaml file on your local machine).
|
||||
For example, run `kubectl get pods/mypod -o yaml > mypod-on-apiserver.yaml` and then
|
||||
manually compare the original pod description, `mypod.yaml` with the one you got
|
||||
back from apiserver, `mypod-on-apiserver.yaml`. There will typically be some
|
||||
lines on the "apiserver" version that are not on the original version. This is
|
||||
expected. However, if there are lines on the original that are not on the apiserver
|
||||
version, then this may indicate a problem with your pod spec.
|
||||
-->
|
||||
接下来就要检查的是 API 服务器上的 Pod 与你所期望创建的是否匹配
|
||||
(例如,你原本使用本机上的一个 YAML 文件来创建 Pod)。
|
||||
例如,运行 `kubectl get pods/mypod -o yaml > mypod-on-apiserver.yaml`,之后
|
||||
手动比较 `mypod.yaml` 与从 API 服务器取回的 Pod 描述。
|
||||
从 API 服务器处获得的 YAML 通常包含一些创建 Pod 所用的 YAML 中不存在的行,这是正常的。
|
||||
不过,如果如果源文件中有些行在 API 服务器版本中不存在,则意味着
|
||||
Pod 规约是有问题的。
|
||||
|
||||
<!--
|
||||
### Debugging Replication Controllers
|
||||
|
||||
Replication controllers are fairly straightforward. They can either create Pods or they can't. If they can't
|
||||
create pods, then please refer to the [instructions above](#debugging-pods) to debug your pods.
|
||||
|
||||
You can also use `kubectl describe rc ${CONTROLLER_NAME}` to introspect events related to the replication
|
||||
controller.
|
||||
-->
|
||||
### 调试副本控制器 {#debugging-replication-controllers}
|
||||
|
||||
副本控制器相对比较简单直接。它们要么能创建 Pod,要么不能。
|
||||
如果不能创建 Pod,请参阅[上述说明](#debugging-pods)调试 Pod。
|
||||
|
||||
你也可以使用 `kubectl describe rc ${CONTROLLER_NAME}` 命令来检视副本控制器相关的事件。
|
||||
|
||||
<!--
|
||||
### Debugging Services
|
||||
|
||||
Services provide load balancing across a set of pods. There are several common problems that can make Services
|
||||
not work properly. The following instructions should help debug Service problems.
|
||||
|
||||
First, verify that there are endpoints for the service. For every Service object, the apiserver makes an `endpoints` resource available.
|
||||
|
||||
You can view this resource with:
|
||||
-->
|
||||
### 调试 Service {#debugging-services}
|
||||
|
||||
服务支持在多个 Pod 间负载均衡。
|
||||
有一些常见的问题可以造成服务无法正常工作。
|
||||
以下说明将有助于调试服务的问题。
|
||||
|
||||
首先,验证服务是否有端点。对于每一个 Service 对象,API 服务器为其提供
|
||||
对应的 `endpoints` 资源。
|
||||
|
||||
通过如下命令可以查看 endpoints 资源:
|
||||
|
||||
```shell
|
||||
kubectl get endpoints ${SERVICE_NAME}
|
||||
```
|
||||
|
||||
<!--
|
||||
Make sure that the endpoints match up with the number of pods that you expect to be members of your service.
|
||||
For example, if your Service is for an nginx container with 3 replicas, you would expect to see three different
|
||||
IP addresses in the Service's endpoints.
|
||||
-->
|
||||
确保 Endpoints 与服务成员 Pod 个数一致。
|
||||
例如,如果你的 Service 用来运行 3 个副本的 nginx 容器,你应该会在 Service 的 Endpoints
|
||||
中看到 3 个不同的 IP 地址。
|
||||
|
||||
<!--
|
||||
#### My service is missing endpoints
|
||||
|
||||
If you are missing endpoints, try listing pods using the labels that Service uses. Imagine that you have
|
||||
a Service where the labels are:
|
||||
-->
|
||||
#### 服务缺少 Endpoints
|
||||
|
||||
如果没有 Endpoints,请尝试使用 Service 所使用的标签列出 Pod。
|
||||
假定你的服务包含如下标签选择算符:
|
||||
|
||||
```yaml
|
||||
...
|
||||
spec:
|
||||
- selector:
|
||||
name: nginx
|
||||
type: frontend
|
||||
```
|
||||
|
||||
<!--
|
||||
You can use:
|
||||
```shell
|
||||
kubectl get pods --selector=name=nginx,type=frontend
|
||||
```
|
||||
|
||||
to list pods that match this selector. Verify that the list matches the Pods that you expect to provide your Service.
|
||||
-->
|
||||
|
||||
你可以使用如下命令列出与选择算符相匹配的 Pod,并验证这些 Pod 是否归属于创建的服务:
|
||||
|
||||
```shell
|
||||
kubectl get pods --selector=name=nginx,type=frontend
|
||||
```
|
||||
|
||||
<!--
|
||||
Verify that the pod's `containerPort` matches up with the Service's `targetPort`
|
||||
-->
|
||||
验证 Pod 的 `containerPort` 与服务的 `targetPort` 是否匹配。
|
||||
|
||||
<!--
|
||||
#### Network traffic is not forwarded
|
||||
|
||||
Please see [debugging service](/docs/tasks/debug/debug-applications/debug-service/) for more information.
|
||||
-->
|
||||
#### 网络流量未被转发
|
||||
|
||||
请参阅[调试 Service](/zh/docs/tasks/debug/debug-applications/debug-service/) 了解更多信息。
|
||||
|
||||
## {{% heading "whatsnext" %}}
|
||||
|
||||
<!--
|
||||
If none of the above solves your problem, follow the instructions in
|
||||
[Debugging Service document](/docs/tasks/debug/debug-applications/debug-service/)
|
||||
to make sure that your `Service` is running, has `Endpoints`, and your `Pods` are
|
||||
actually serving; you have DNS working, iptables rules installed, and kube-proxy
|
||||
does not seem to be misbehaving.
|
||||
|
||||
You may also visit [troubleshooting document](/docs/tasks/debug/overview/) for more information.
|
||||
-->
|
||||
如果上述方法都不能解决你的问题,
|
||||
请按照[调试 Service 文档](/zh/docs/tasks/debug/debug-applications/debug-service/)中的介绍,
|
||||
确保你的 `Service` 处于 Running 态,有 `Endpoints` 被创建,`Pod` 真的在提供服务;
|
||||
DNS 服务已配置并正常工作,iptables 规则也以安装并且 `kube-proxy` 也没有异常行为。
|
||||
|
||||
你也可以访问[故障排查文档](/zh/docs/tasks/debug/overview/)来获取更多信息。
|
||||
@@ -0,0 +1,916 @@
|
||||
---
|
||||
title: 调试运行中的 Pod
|
||||
content_type: task
|
||||
---
|
||||
|
||||
<!--
|
||||
reviewers:
|
||||
- verb
|
||||
- soltysh
|
||||
title: Debug Running Pods
|
||||
content_type: task
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
<!--
|
||||
This page explains how to debug Pods running (or crashing) on a Node.
|
||||
-->
|
||||
本页解释如何在节点上调试运行中(或崩溃)的 Pod。
|
||||
|
||||
## {{% heading "prerequisites" %}}
|
||||
|
||||
<!--
|
||||
* Your {{< glossary_tooltip text="Pod" term_id="pod" >}} should already be
|
||||
scheduled and running. If your Pod is not yet running, start with [Debugging
|
||||
Pods](/docs/tasks/debug/debug-application/).
|
||||
* For some of the advanced debugging steps you need to know on which Node the
|
||||
Pod is running and have shell access to run commands on that Node. You don't
|
||||
need that access to run the standard debug steps that use `kubectl`.
|
||||
-->
|
||||
* 你的 {{< glossary_tooltip text="Pod" term_id="pod" >}} 应该已经被调度并正在运行中,
|
||||
如果你的 Pod 还没有运行,请参阅[调试 Pod](/zh/docs/tasks/debug/debug-application/)。
|
||||
|
||||
* 对于一些高级调试步骤,你应该知道 Pod 具体运行在哪个节点上,并具有在该节点上运行命令的 shell 访问权限。
|
||||
你不需要任何访问权限就可以使用 `kubectl` 去运行一些标准调试步骤。
|
||||
|
||||
<!--
|
||||
## Using `kubectl describe pod` to fetch details about pods
|
||||
-->
|
||||
## 使用 `kubectl describe pod` 命令获取 Pod 详情
|
||||
|
||||
<!--
|
||||
For this example we'll use a Deployment to create two pods, similar to the earlier example.
|
||||
-->
|
||||
与之前的例子类似,我们使用一个 Deployment 来创建两个 Pod。
|
||||
|
||||
{{< codenew file="application/nginx-with-request.yaml" >}}
|
||||
|
||||
<!--
|
||||
Create deployment by running following command:
|
||||
-->
|
||||
使用如下命令创建 Deployment:
|
||||
|
||||
```shell
|
||||
kubectl apply -f https://k8s.io/examples/application/nginx-with-request.yaml
|
||||
```
|
||||
|
||||
```
|
||||
deployment.apps/nginx-deployment created
|
||||
```
|
||||
|
||||
<!--
|
||||
Check pod status by following command:
|
||||
-->
|
||||
使用如下命令查看 Pod 状态:
|
||||
|
||||
```shell
|
||||
kubectl get pods
|
||||
```
|
||||
|
||||
```
|
||||
NAME READY STATUS RESTARTS AGE
|
||||
nginx-deployment-67d4bdd6f5-cx2nz 1/1 Running 0 13s
|
||||
nginx-deployment-67d4bdd6f5-w6kd7 1/1 Running 0 13s
|
||||
```
|
||||
|
||||
<!--
|
||||
We can retrieve a lot more information about each of these pods using `kubectl describe pod`. For example:
|
||||
-->
|
||||
我们可以使用 `kubectl describe pod` 命令来查询每个 Pod 的更多信息,比如:
|
||||
|
||||
```shell
|
||||
kubectl describe pod nginx-deployment-67d4bdd6f5-w6kd7
|
||||
```
|
||||
|
||||
```none
|
||||
Name: nginx-deployment-67d4bdd6f5-w6kd7
|
||||
Namespace: default
|
||||
Priority: 0
|
||||
Node: kube-worker-1/192.168.0.113
|
||||
Start Time: Thu, 17 Feb 2022 16:51:01 -0500
|
||||
Labels: app=nginx
|
||||
pod-template-hash=67d4bdd6f5
|
||||
Annotations: <none>
|
||||
Status: Running
|
||||
IP: 10.88.0.3
|
||||
IPs:
|
||||
IP: 10.88.0.3
|
||||
IP: 2001:db8::1
|
||||
Controlled By: ReplicaSet/nginx-deployment-67d4bdd6f5
|
||||
Containers:
|
||||
nginx:
|
||||
Container ID: containerd://5403af59a2b46ee5a23fb0ae4b1e077f7ca5c5fb7af16e1ab21c00e0e616462a
|
||||
Image: nginx
|
||||
Image ID: docker.io/library/nginx@sha256:2834dc507516af02784808c5f48b7cbe38b8ed5d0f4837f16e78d00deb7e7767
|
||||
Port: 80/TCP
|
||||
Host Port: 0/TCP
|
||||
State: Running
|
||||
Started: Thu, 17 Feb 2022 16:51:05 -0500
|
||||
Ready: True
|
||||
Restart Count: 0
|
||||
Limits:
|
||||
cpu: 500m
|
||||
memory: 128Mi
|
||||
Requests:
|
||||
cpu: 500m
|
||||
memory: 128Mi
|
||||
Environment: <none>
|
||||
Mounts:
|
||||
/var/run/secrets/kubernetes.io/serviceaccount from kube-api-access-bgsgp (ro)
|
||||
Conditions:
|
||||
Type Status
|
||||
Initialized True
|
||||
Ready True
|
||||
ContainersReady True
|
||||
PodScheduled True
|
||||
Volumes:
|
||||
kube-api-access-bgsgp:
|
||||
Type: Projected (a volume that contains injected data from multiple sources)
|
||||
TokenExpirationSeconds: 3607
|
||||
ConfigMapName: kube-root-ca.crt
|
||||
ConfigMapOptional: <nil>
|
||||
DownwardAPI: true
|
||||
QoS Class: Guaranteed
|
||||
Node-Selectors: <none>
|
||||
Tolerations: node.kubernetes.io/not-ready:NoExecute op=Exists for 300s
|
||||
node.kubernetes.io/unreachable:NoExecute op=Exists for 300s
|
||||
Events:
|
||||
Type Reason Age From Message
|
||||
---- ------ ---- ---- -------
|
||||
Normal Scheduled 34s default-scheduler Successfully assigned default/nginx-deployment-67d4bdd6f5-w6kd7 to kube-worker-1
|
||||
Normal Pulling 31s kubelet Pulling image "nginx"
|
||||
Normal Pulled 30s kubelet Successfully pulled image "nginx" in 1.146417389s
|
||||
Normal Created 30s kubelet Created container nginx
|
||||
Normal Started 30s kubelet Started container nginx
|
||||
```
|
||||
|
||||
<!--
|
||||
Here you can see configuration information about the container(s) and Pod (labels, resource requirements, etc.), as well as status information about the container(s) and Pod (state, readiness, restart count, events, etc.).
|
||||
-->
|
||||
在这里,你可以看到有关容器和 Pod 的配置信息(标签、资源需求等),
|
||||
以及有关容器和 Pod 的状态信息(状态、就绪、重启计数、事件等) 。
|
||||
|
||||
<!--
|
||||
The container state is one of Waiting, Running, or Terminated. Depending on the state, additional information will be provided -- here you can see that for a container in Running state, the system tells you when the container started.
|
||||
-->
|
||||
容器状态是 Waiting、Running 和 Terminated 之一。
|
||||
根据状态的不同,还有对应的额外的信息 —— 在这里你可以看到,
|
||||
对于处于运行状态的容器,系统会告诉你容器的启动时间。
|
||||
|
||||
<!--
|
||||
Ready tells you whether the container passed its last readiness probe. (In this case, the container does not have a readiness probe configured; the container is assumed to be ready if no readiness probe is configured.)
|
||||
-->
|
||||
Ready 指示是否通过了最后一个就绪态探测。
|
||||
(在本例中,容器没有配置就绪态探测;如果没有配置就绪态探测,则假定容器已经就绪。)
|
||||
|
||||
<!--
|
||||
Restart Count tells you how many times the container has been restarted; this information can be useful for detecting crash loops in containers that are configured with a restart policy of 'always.'
|
||||
-->
|
||||
Restart Count 告诉你容器已重启的次数;
|
||||
这些信息对于定位配置了 “Always” 重启策略的容器持续崩溃问题非常有用。
|
||||
|
||||
<!--
|
||||
Currently the only Condition associated with a Pod is the binary Ready condition, which indicates that the pod is able to service requests and should be added to the load balancing pools of all matching services.
|
||||
-->
|
||||
目前,唯一与 Pod 有关的状态是 Ready 状况,该状况表明 Pod 能够为请求提供服务,
|
||||
并且应该添加到相应服务的负载均衡池中。
|
||||
|
||||
<!--
|
||||
Lastly, you see a log of recent events related to your Pod. The system compresses multiple identical events by indicating the first and last time it was seen and the number of times it was seen. "From" indicates the component that is logging the event, "SubobjectPath" tells you which object (e.g. container within the pod) is being referred to, and "Reason" and "Message" tell you what happened.
|
||||
-->
|
||||
最后,你还可以看到与 Pod 相关的近期事件。
|
||||
系统通过指示第一次和最后一次看到事件以及看到该事件的次数来压缩多个相同的事件。
|
||||
“From” 标明记录事件的组件,
|
||||
“SubobjectPath” 告诉你引用了哪个对象(例如 Pod 中的容器),
|
||||
“Reason” 和 “Message” 告诉你发生了什么。
|
||||
|
||||
<!--
|
||||
## Example: debugging Pending Pods
|
||||
|
||||
A common scenario that you can detect using events is when you've created a Pod that won't fit on any node. For example, the Pod might request more resources than are free on any node, or it might specify a label selector that doesn't match any nodes. Let's say we created the previous Deployment with 5 replicas (instead of 2) and requesting 600 millicores instead of 500, on a four-node cluster where each (virtual) machine has 1 CPU. In that case one of the Pods will not be able to schedule. (Note that because of the cluster addon pods such as fluentd, skydns, etc., that run on each node, if we requested 1000 millicores then none of the Pods would be able to schedule.)
|
||||
-->
|
||||
## 例子: 调试 Pending 状态的 Pod
|
||||
|
||||
可以使用事件来调试的一个常见的场景是,你创建 Pod 无法被调度到任何节点。
|
||||
比如,Pod 请求的资源比较多,没有任何一个节点能够满足,或者它指定了一个标签,没有节点可匹配。
|
||||
假定我们创建之前的 Deployment 时指定副本数是 5(不再是 2),并且请求 600 毫核(不再是 500),
|
||||
对于一个 4 个节点的集群,若每个节点只有 1 个 CPU,这时至少有一个 Pod 不能被调度。
|
||||
(需要注意的是,其他集群插件 Pod,比如 fluentd、skydns 等等会在每个节点上运行,
|
||||
如果我们需求 1000 毫核,将不会有 Pod 会被调度。)
|
||||
|
||||
```shell
|
||||
kubectl get pods
|
||||
```
|
||||
|
||||
```
|
||||
NAME READY STATUS RESTARTS AGE
|
||||
nginx-deployment-1006230814-6winp 1/1 Running 0 7m
|
||||
nginx-deployment-1006230814-fmgu3 1/1 Running 0 7m
|
||||
nginx-deployment-1370807587-6ekbw 1/1 Running 0 1m
|
||||
nginx-deployment-1370807587-fg172 0/1 Pending 0 1m
|
||||
nginx-deployment-1370807587-fz9sd 0/1 Pending 0 1m
|
||||
```
|
||||
|
||||
<!--
|
||||
To find out why the nginx-deployment-1370807587-fz9sd pod is not running, we can use `kubectl describe pod` on the pending Pod and look at its events:
|
||||
-->
|
||||
为了查找 Pod nginx-deployment-1370807587-fz9sd 没有运行的原因,我们可以使用
|
||||
`kubectl describe pod` 命令描述 Pod,查看其事件:
|
||||
|
||||
```shell
|
||||
kubectl describe pod nginx-deployment-1370807587-fz9sd
|
||||
```
|
||||
|
||||
```none
|
||||
Name: nginx-deployment-1370807587-fz9sd
|
||||
Namespace: default
|
||||
Node: /
|
||||
Labels: app=nginx,pod-template-hash=1370807587
|
||||
Status: Pending
|
||||
IP:
|
||||
Controllers: ReplicaSet/nginx-deployment-1370807587
|
||||
Containers:
|
||||
nginx:
|
||||
Image: nginx
|
||||
Port: 80/TCP
|
||||
QoS Tier:
|
||||
memory: Guaranteed
|
||||
cpu: Guaranteed
|
||||
Limits:
|
||||
cpu: 1
|
||||
memory: 128Mi
|
||||
Requests:
|
||||
cpu: 1
|
||||
memory: 128Mi
|
||||
Environment Variables:
|
||||
Volumes:
|
||||
default-token-4bcbi:
|
||||
Type: Secret (a volume populated by a Secret)
|
||||
SecretName: default-token-4bcbi
|
||||
Events:
|
||||
FirstSeen LastSeen Count From SubobjectPath Type Reason Message
|
||||
--------- -------- ----- ---- ------------- -------- ------ -------
|
||||
1m 48s 7 {default-scheduler } Warning FailedScheduling pod (nginx-deployment-1370807587-fz9sd) failed to fit in any node
|
||||
fit failure on node (kubernetes-node-6ta5): Node didn't have enough resource: CPU, requested: 1000, used: 1420, capacity: 2000
|
||||
fit failure on node (kubernetes-node-wul5): Node didn't have enough resource: CPU, requested: 1000, used: 1100, capacity: 2000
|
||||
```
|
||||
|
||||
<!--
|
||||
Here you can see the event generated by the scheduler saying that the Pod failed to schedule for reason `FailedScheduling` (and possibly others). The message tells us that there were not enough resources for the Pod on any of the nodes.
|
||||
-->
|
||||
这里你可以看到由调度器记录的事件,它表明了 Pod 不能被调度的原因是 `FailedScheduling`(也可能是其他值)。
|
||||
其 message 部分表明没有任何节点拥有足够多的资源。
|
||||
|
||||
<!--
|
||||
To correct this situation, you can use `kubectl scale` to update your Deployment to specify four or fewer replicas. (Or you could leave the one Pod pending, which is harmless.)
|
||||
-->
|
||||
要纠正这种情况,可以使用 `kubectl scale` 更新 Deployment,以指定 4 个或更少的副本。
|
||||
(或者你可以让 Pod 继续保持这个状态,这是无害的。)
|
||||
|
||||
<!--
|
||||
Events such as the ones you saw at the end of `kubectl describe pod` are persisted in etcd and provide high-level information on what is happening in the cluster. To list all events you can use
|
||||
-->
|
||||
你在 `kubectl describe pod` 结尾处看到的事件都保存在 etcd 中,
|
||||
并提供关于集群中正在发生的事情的高级信息。
|
||||
如果需要列出所有事件,可使用命令:
|
||||
|
||||
```shell
|
||||
kubectl get events
|
||||
```
|
||||
|
||||
<!--
|
||||
but you have to remember that events are namespaced. This means that if you're interested in events for some namespaced object (e.g. what happened with Pods in namespace `my-namespace`) you need to explicitly provide a namespace to the command:
|
||||
-->
|
||||
但是,需要注意的是,事件是区分名字空间的。
|
||||
如果你对某些名字空间域的对象(比如 `my-namespace` 名字下的 Pod)的事件感兴趣,
|
||||
你需要显式地在命令行中指定名字空间:
|
||||
|
||||
```shell
|
||||
kubectl get events --namespace=my-namespace
|
||||
```
|
||||
|
||||
<!--
|
||||
To see events from all namespaces, you can use the `--all-namespaces` argument.
|
||||
-->
|
||||
查看所有 namespace 的事件,可使用 `--all-namespaces` 参数。
|
||||
|
||||
<!--
|
||||
In addition to `kubectl describe pod`, another way to get extra information about a pod (beyond what is provided by `kubectl get pod`) is to pass the `-o yaml` output format flag to `kubectl get pod`. This will give you, in YAML format, even more information than `kubectl describe pod`--essentially all of the information the system has about the Pod. Here you will see things like annotations (which are key-value metadata without the label restrictions, that is used internally by Kubernetes system components), restart policy, ports, and volumes.
|
||||
-->
|
||||
除了 `kubectl describe pod` 以外,另一种获取 Pod 额外信息(除了 `kubectl get pod`)的方法
|
||||
是给 `kubectl get pod` 增加 `-o yaml` 输出格式参数。
|
||||
该命令将以 YAML 格式为你提供比 `kubectl describe pod` 更多的信息 —— 实际上是系统拥有的关于 Pod 的所有信息。
|
||||
在这里,你将看到注解(没有标签限制的键值元数据,由 Kubernetes 系统组件在内部使用)、
|
||||
重启策略、端口和卷等。
|
||||
|
||||
```shell
|
||||
kubectl get pod nginx-deployment-1006230814-6winp -o yaml
|
||||
```
|
||||
|
||||
```yaml
|
||||
apiVersion: v1
|
||||
kind: Pod
|
||||
metadata:
|
||||
creationTimestamp: "2022-02-17T21:51:01Z"
|
||||
generateName: nginx-deployment-67d4bdd6f5-
|
||||
labels:
|
||||
app: nginx
|
||||
pod-template-hash: 67d4bdd6f5
|
||||
name: nginx-deployment-67d4bdd6f5-w6kd7
|
||||
namespace: default
|
||||
ownerReferences:
|
||||
- apiVersion: apps/v1
|
||||
blockOwnerDeletion: true
|
||||
controller: true
|
||||
kind: ReplicaSet
|
||||
name: nginx-deployment-67d4bdd6f5
|
||||
uid: 7d41dfd4-84c0-4be4-88ab-cedbe626ad82
|
||||
resourceVersion: "1364"
|
||||
uid: a6501da1-0447-4262-98eb-c03d4002222e
|
||||
spec:
|
||||
containers:
|
||||
- image: nginx
|
||||
imagePullPolicy: Always
|
||||
name: nginx
|
||||
ports:
|
||||
- containerPort: 80
|
||||
protocol: TCP
|
||||
resources:
|
||||
limits:
|
||||
cpu: 500m
|
||||
memory: 128Mi
|
||||
requests:
|
||||
cpu: 500m
|
||||
memory: 128Mi
|
||||
terminationMessagePath: /dev/termination-log
|
||||
terminationMessagePolicy: File
|
||||
volumeMounts:
|
||||
- mountPath: /var/run/secrets/kubernetes.io/serviceaccount
|
||||
name: kube-api-access-bgsgp
|
||||
readOnly: true
|
||||
dnsPolicy: ClusterFirst
|
||||
enableServiceLinks: true
|
||||
nodeName: kube-worker-1
|
||||
preemptionPolicy: PreemptLowerPriority
|
||||
priority: 0
|
||||
restartPolicy: Always
|
||||
schedulerName: default-scheduler
|
||||
securityContext: {}
|
||||
serviceAccount: default
|
||||
serviceAccountName: default
|
||||
terminationGracePeriodSeconds: 30
|
||||
tolerations:
|
||||
- effect: NoExecute
|
||||
key: node.kubernetes.io/not-ready
|
||||
operator: Exists
|
||||
tolerationSeconds: 300
|
||||
- effect: NoExecute
|
||||
key: node.kubernetes.io/unreachable
|
||||
operator: Exists
|
||||
tolerationSeconds: 300
|
||||
volumes:
|
||||
- name: kube-api-access-bgsgp
|
||||
projected:
|
||||
defaultMode: 420
|
||||
sources:
|
||||
- serviceAccountToken:
|
||||
expirationSeconds: 3607
|
||||
path: token
|
||||
- configMap:
|
||||
items:
|
||||
- key: ca.crt
|
||||
path: ca.crt
|
||||
name: kube-root-ca.crt
|
||||
- downwardAPI:
|
||||
items:
|
||||
- fieldRef:
|
||||
apiVersion: v1
|
||||
fieldPath: metadata.namespace
|
||||
path: namespace
|
||||
status:
|
||||
conditions:
|
||||
- lastProbeTime: null
|
||||
lastTransitionTime: "2022-02-17T21:51:01Z"
|
||||
status: "True"
|
||||
type: Initialized
|
||||
- lastProbeTime: null
|
||||
lastTransitionTime: "2022-02-17T21:51:06Z"
|
||||
status: "True"
|
||||
type: Ready
|
||||
- lastProbeTime: null
|
||||
lastTransitionTime: "2022-02-17T21:51:06Z"
|
||||
status: "True"
|
||||
type: ContainersReady
|
||||
- lastProbeTime: null
|
||||
lastTransitionTime: "2022-02-17T21:51:01Z"
|
||||
status: "True"
|
||||
type: PodScheduled
|
||||
containerStatuses:
|
||||
- containerID: containerd://5403af59a2b46ee5a23fb0ae4b1e077f7ca5c5fb7af16e1ab21c00e0e616462a
|
||||
image: docker.io/library/nginx:latest
|
||||
imageID: docker.io/library/nginx@sha256:2834dc507516af02784808c5f48b7cbe38b8ed5d0f4837f16e78d00deb7e7767
|
||||
lastState: {}
|
||||
name: nginx
|
||||
ready: true
|
||||
restartCount: 0
|
||||
started: true
|
||||
state:
|
||||
running:
|
||||
startedAt: "2022-02-17T21:51:05Z"
|
||||
hostIP: 192.168.0.113
|
||||
phase: Running
|
||||
podIP: 10.88.0.3
|
||||
podIPs:
|
||||
- ip: 10.88.0.3
|
||||
- ip: 2001:db8::1
|
||||
qosClass: Guaranteed
|
||||
startTime: "2022-02-17T21:51:01Z"
|
||||
```
|
||||
|
||||
<!--
|
||||
## Examining pod logs {#examine-pod-logs}
|
||||
|
||||
First, look at the logs of the affected container:
|
||||
|
||||
```shell
|
||||
kubectl logs ${POD_NAME} ${CONTAINER_NAME}
|
||||
```
|
||||
|
||||
If your container has previously crashed, you can access the previous container's crash log with:
|
||||
|
||||
```shell
|
||||
kubectl logs --previous ${POD_NAME} ${CONTAINER_NAME}
|
||||
```
|
||||
-->
|
||||
## 检查 Pod 的日志 {#examine-pod-logs}
|
||||
|
||||
首先,查看受到影响的容器的日志:
|
||||
|
||||
```shell
|
||||
kubectl logs ${POD_NAME} ${CONTAINER_NAME}
|
||||
```
|
||||
|
||||
如果你的容器之前崩溃过,你可以通过下面命令访问之前容器的崩溃日志:
|
||||
|
||||
```shell
|
||||
kubectl logs --previous ${POD_NAME} ${CONTAINER_NAME}
|
||||
```
|
||||
|
||||
<!--
|
||||
## Debugging with container exec {#container-exec}
|
||||
|
||||
If the {{< glossary_tooltip text="container image" term_id="image" >}} includes
|
||||
debugging utilities, as is the case with images built from Linux and Windows OS
|
||||
base images, you can run commands inside a specific container with
|
||||
`kubectl exec`:
|
||||
|
||||
```shell
|
||||
kubectl exec ${POD_NAME} -c ${CONTAINER_NAME} -- ${CMD} ${ARG1} ${ARG2} ... ${ARGN}
|
||||
```
|
||||
|
||||
{{< note >}}
|
||||
`-c ${CONTAINER_NAME}` is optional. You can omit it for Pods that only contain a single container.
|
||||
{{< /note >}}
|
||||
|
||||
As an example, to look at the logs from a running Cassandra pod, you might run
|
||||
|
||||
```shell
|
||||
kubectl exec cassandra -- cat /var/log/cassandra/system.log
|
||||
```
|
||||
|
||||
You can run a shell that's connected to your terminal using the `-i` and `-t`
|
||||
arguments to `kubectl exec`, for example:
|
||||
|
||||
```shell
|
||||
kubectl exec -it cassandra -- sh
|
||||
```
|
||||
|
||||
For more details, see [Get a Shell to a Running Container](
|
||||
/docs/tasks/debug/debug-application/get-shell-running-container/).
|
||||
-->
|
||||
## 使用容器 exec 进行调试 {#container-exec}
|
||||
|
||||
如果 {{< glossary_tooltip text="容器镜像" term_id="image" >}} 包含调试程序,
|
||||
比如从 Linux 和 Windows 操作系统基础镜像构建的镜像,你可以使用 `kubectl exec` 命令
|
||||
在特定的容器中运行一些命令:
|
||||
|
||||
```shell
|
||||
kubectl exec ${POD_NAME} -c ${CONTAINER_NAME} -- ${CMD} ${ARG1} ${ARG2} ... ${ARGN}
|
||||
```
|
||||
{{< note >}}
|
||||
`-c ${CONTAINER_NAME}` 是可选择的。如果Pod中仅包含一个容器,就可以忽略它。
|
||||
{{< /note >}}
|
||||
|
||||
例如,要查看正在运行的 Cassandra pod中的日志,可以运行:
|
||||
|
||||
```shell
|
||||
kubectl exec cassandra -- cat /var/log/cassandra/system.log
|
||||
```
|
||||
|
||||
你可以在 `kubectl exec` 命令后面加上 `-i` 和 `-t` 来运行一个连接到你的终端的 Shell,比如:
|
||||
|
||||
```shell
|
||||
kubectl exec -it cassandra -- sh
|
||||
```
|
||||
|
||||
若要了解更多内容,可查看[获取正在运行容器的 Shell](/zh/docs/tasks/debug/debug-application/get-shell-running-container/)。
|
||||
|
||||
<!--
|
||||
## Debugging with an ephemeral debug container {#ephemeral-container}
|
||||
|
||||
{{< feature-state state="beta" for_k8s_version="v1.23" >}}
|
||||
|
||||
{{< glossary_tooltip text="Ephemeral containers" term_id="ephemeral-container" >}}
|
||||
are useful for interactive troubleshooting when `kubectl exec` is insufficient
|
||||
because a container has crashed or a container image doesn't include debugging
|
||||
utilities, such as with [distroless images](
|
||||
https://github.com/GoogleContainerTools/distroless).
|
||||
-->
|
||||
## 使用临时调试容器来进行调试 {#ephemeral-container}
|
||||
|
||||
{{< feature-state state="beta" for_k8s_version="v1.23" >}}
|
||||
|
||||
当由于容器崩溃或容器镜像不包含调试程序(例如[无发行版镜像](https://github.com/GoogleContainerTools/distroless)等)
|
||||
而导致 `kubectl exec` 无法运行时,{{< glossary_tooltip text="临时容器" term_id="ephemeral-container" >}}对于排除交互式故障很有用。
|
||||
|
||||
<!--
|
||||
### Example debugging using ephemeral containers {#ephemeral-container-example}
|
||||
|
||||
You can use the `kubectl debug` command to add ephemeral containers to a
|
||||
running Pod. First, create a pod for the example:
|
||||
|
||||
```shell
|
||||
kubectl run ephemeral-demo --image=k8s.gcr.io/pause:3.1 --restart=Never
|
||||
```
|
||||
|
||||
The examples in this section use the `pause` container image because it does not
|
||||
contain debugging utilities, but this method works with all container
|
||||
images.
|
||||
-->
|
||||
## 使用临时容器来调试的例子 {#ephemeral-container-example}
|
||||
|
||||
你可以使用 `kubectl debug` 命令来给正在运行中的 Pod 增加一个临时容器。
|
||||
首先,像示例一样创建一个 pod:
|
||||
|
||||
```shell
|
||||
kubectl run ephemeral-demo --image=k8s.gcr.io/pause:3.1 --restart=Never
|
||||
```
|
||||
|
||||
{{< note >}}
|
||||
本节示例中使用 `pause` 容器镜像,因为它不包含调试程序,但是这个方法适用于所有容器镜像。
|
||||
{{< /note >}}
|
||||
|
||||
<!--
|
||||
If you attempt to use `kubectl exec` to create a shell you will see an error
|
||||
because there is no shell in this container image.
|
||||
-->
|
||||
如果你尝试使用 `kubectl exec` 来创建一个 shell,你将会看到一个错误,因为这个容器镜像中没有 shell。
|
||||
|
||||
```shell
|
||||
kubectl exec -it ephemeral-demo -- sh
|
||||
```
|
||||
|
||||
```
|
||||
OCI runtime exec failed: exec failed: container_linux.go:346: starting container process caused "exec: \"sh\": executable file not found in $PATH": unknown
|
||||
```
|
||||
|
||||
<!--
|
||||
You can instead add a debugging container using `kubectl debug`. If you
|
||||
specify the `-i`/`--interactive` argument, `kubectl` will automatically attach
|
||||
to the console of the Ephemeral Container.
|
||||
-->
|
||||
|
||||
你可以改为使用 `kubectl debug` 添加调试容器。
|
||||
如果你指定 `-i` 或者 `--interactive` 参数,`kubectl` 将自动挂接到临时容器的控制台。
|
||||
|
||||
```shell
|
||||
kubectl debug -it ephemeral-demo --image=busybox:1.28 --target=ephemeral-demo
|
||||
```
|
||||
|
||||
```
|
||||
Defaulting debug container name to debugger-8xzrl.
|
||||
If you don't see a command prompt, try pressing enter.
|
||||
/ #
|
||||
```
|
||||
|
||||
<!--
|
||||
This command adds a new busybox container and attaches to it. The `--target`
|
||||
parameter targets the process namespace of another container. It's necessary
|
||||
here because `kubectl run` does not enable [process namespace sharing](
|
||||
/docs/tasks/configure-pod-container/share-process-namespace/) in the pod it
|
||||
creates.
|
||||
|
||||
{{< note >}}
|
||||
The `--target` parameter must be supported by the {{< glossary_tooltip
|
||||
text="Container Runtime" term_id="container-runtime" >}}. When not supported,
|
||||
the Ephemeral Container may not be started, or it may be started with an
|
||||
isolated process namespace so that `ps` does not reveal processes in other
|
||||
containers.
|
||||
{{< /note >}}
|
||||
|
||||
You can view the state of the newly created ephemeral container using `kubectl describe`:
|
||||
-->
|
||||
此命令添加一个新的 busybox 容器并将其挂接到该容器。`--target` 参数指定另一个容器的进程命名空间。
|
||||
这是必需的,因为 `kubectl run` 不能在它创建的pod中启用
|
||||
[共享进程命名空间](/zh/docs/tasks/configure-pod-container/share-process-namespace/)。
|
||||
|
||||
{{< note >}}
|
||||
{{< glossary_tooltip text="容器运行时" term_id="container-runtime" >}}必须支持 `--target` 参数。
|
||||
如果不支持,则临时容器可能不会启动,或者可能使用隔离的进程命名空间启动,
|
||||
以便 `ps` 不显示其他容器内的进程。
|
||||
{{< /note >}}
|
||||
|
||||
你可以使用 `kubectl describe` 查看新创建的临时容器的状态:
|
||||
|
||||
```shell
|
||||
kubectl describe pod ephemeral-demo
|
||||
```
|
||||
|
||||
```
|
||||
...
|
||||
Ephemeral Containers:
|
||||
debugger-8xzrl:
|
||||
Container ID: docker://b888f9adfd15bd5739fefaa39e1df4dd3c617b9902082b1cfdc29c4028ffb2eb
|
||||
Image: busybox
|
||||
Image ID: docker-pullable://busybox@sha256:1828edd60c5efd34b2bf5dd3282ec0cc04d47b2ff9caa0b6d4f07a21d1c08084
|
||||
Port: <none>
|
||||
Host Port: <none>
|
||||
State: Running
|
||||
Started: Wed, 12 Feb 2020 14:25:42 +0100
|
||||
Ready: False
|
||||
Restart Count: 0
|
||||
Environment: <none>
|
||||
Mounts: <none>
|
||||
...
|
||||
```
|
||||
|
||||
<!--
|
||||
Use `kubectl delete` to remove the Pod when you're finished:
|
||||
-->
|
||||
使用 `kubectl delete` 来移除已经结束掉的 Pod:
|
||||
|
||||
```shell
|
||||
kubectl delete pod ephemeral-demo
|
||||
```
|
||||
|
||||
<!--
|
||||
## Debugging using a copy of the Pod
|
||||
-->
|
||||
## 通过 Pod 副本调试
|
||||
|
||||
<!--
|
||||
Sometimes Pod configuration options make it difficult to troubleshoot in certain
|
||||
situations. For example, you can't run `kubectl exec` to troubleshoot your
|
||||
container if your container image does not include a shell or if your application
|
||||
crashes on startup. In these situations you can use `kubectl debug` to create a
|
||||
copy of the Pod with configuration values changed to aid debugging.
|
||||
-->
|
||||
有些时候 Pod 的配置参数使得在某些情况下很难执行故障排查。
|
||||
例如,在容器镜像中不包含 shell 或者你的应用程序在启动时崩溃的情况下,
|
||||
就不能通过运行 `kubectl exec` 来排查容器故障。
|
||||
在这些情况下,你可以使用 `kubectl debug` 来创建 Pod 的副本,通过更改配置帮助调试。
|
||||
|
||||
<!--
|
||||
### Copying a Pod while adding a new container
|
||||
-->
|
||||
### 在添加新的容器时创建 Pod 副本
|
||||
|
||||
<!--
|
||||
Adding a new container can be useful when your application is running but not
|
||||
behaving as you expect and you'd like to add additional troubleshooting
|
||||
utilities to the Pod.
|
||||
-->
|
||||
当应用程序正在运行但其表现不符合预期时,你会希望在 Pod 中添加额外的调试工具,
|
||||
这时添加新容器是很有用的。
|
||||
|
||||
<!--
|
||||
For example, maybe your application's container images are built on `busybox`
|
||||
but you need debugging utilities not included in `busybox`. You can simulate
|
||||
this scenario using `kubectl run`:
|
||||
-->
|
||||
例如,应用的容器镜像是建立在 `busybox` 的基础上,
|
||||
但是你需要 `busybox` 中并不包含的调试工具。
|
||||
你可以使用 `kubectl run` 模拟这个场景:
|
||||
|
||||
```shell
|
||||
kubectl run myapp --image=busybox:1.28 --restart=Never -- sleep 1d
|
||||
```
|
||||
<!--
|
||||
Run this command to create a copy of `myapp` named `myapp-debug` that adds a
|
||||
new Ubuntu container for debugging:
|
||||
-->
|
||||
通过运行以下命令,建立 `myapp` 的一个名为 `myapp-debug` 的副本,
|
||||
新增了一个用于调试的 Ubuntu 容器,
|
||||
|
||||
```shell
|
||||
kubectl debug myapp -it --image=ubuntu --share-processes --copy-to=myapp-debug
|
||||
```
|
||||
|
||||
```
|
||||
Defaulting debug container name to debugger-w7xmf.
|
||||
If you don't see a command prompt, try pressing enter.
|
||||
root@myapp-debug:/#
|
||||
```
|
||||
<!--
|
||||
* `kubectl debug` automatically generates a container name if you don't choose
|
||||
one using the `--container` flag.
|
||||
* The `-i` flag causes `kubectl debug` to attach to the new container by
|
||||
default. You can prevent this by specifying `--attach=false`. If your session
|
||||
becomes disconnected you can reattach using `kubectl attach`.
|
||||
* The `--share-processes` allows the containers in this Pod to see processes
|
||||
from the other containers in the Pod. For more information about how this
|
||||
works, see [Share Process Namespace between Containers in a Pod](
|
||||
/docs/tasks/configure-pod-container/share-process-namespace/).
|
||||
-->
|
||||
{{< note >}}
|
||||
* 如果你没有使用 `--container` 指定新的容器名,`kubectl debug` 会自动生成的。
|
||||
* 默认情况下,`-i` 标志使 `kubectl debug` 附加到新容器上。
|
||||
你可以通过指定 `--attach=false` 来防止这种情况。
|
||||
如果你的会话断开连接,你可以使用 `kubectl attach` 重新连接。
|
||||
* `--share-processes` 允许在此 Pod 中的其他容器中查看该容器的进程。
|
||||
参阅[在 Pod 中的容器之间共享进程命名空间](/zh/docs/tasks/configure-pod-container/share-process-namespace/)
|
||||
获取更多信息。
|
||||
{{< /note >}}
|
||||
|
||||
<!--
|
||||
Don't forget to clean up the debugging Pod when you're finished with it:
|
||||
-->
|
||||
不要忘了清理调试 Pod:
|
||||
|
||||
```shell
|
||||
kubectl delete pod myapp myapp-debug
|
||||
```
|
||||
|
||||
<!--
|
||||
### Copying a Pod while changing its command
|
||||
-->
|
||||
### 在改变 Pod 命令时创建 Pod 副本
|
||||
|
||||
<!--
|
||||
Sometimes it's useful to change the command for a container, for example to
|
||||
add a debugging flag or because the application is crashing.
|
||||
-->
|
||||
有时更改容器的命令很有用,例如添加调试标志或因为应用崩溃。
|
||||
|
||||
<!--
|
||||
To simulate a crashing application, use `kubectl run` to create a container
|
||||
that immediately exits:
|
||||
-->
|
||||
为了模拟应用崩溃的场景,使用 `kubectl run` 命令创建一个立即退出的容器:
|
||||
|
||||
```
|
||||
kubectl run --image=busybox:1.28 myapp -- false
|
||||
```
|
||||
|
||||
<!--
|
||||
You can see using `kubectl describe pod myapp` that this container is crashing:
|
||||
-->
|
||||
使用 `kubectl describe pod myapp` 命令,你可以看到容器崩溃了:
|
||||
|
||||
```
|
||||
Containers:
|
||||
myapp:
|
||||
Image: busybox
|
||||
...
|
||||
Args:
|
||||
false
|
||||
State: Waiting
|
||||
Reason: CrashLoopBackOff
|
||||
Last State: Terminated
|
||||
Reason: Error
|
||||
Exit Code: 1
|
||||
```
|
||||
|
||||
<!--
|
||||
You can use `kubectl debug` to create a copy of this Pod with the command
|
||||
changed to an interactive shell:
|
||||
-->
|
||||
你可以使用 `kubectl debug` 命令创建该 Pod 的一个副本,
|
||||
在该副本中命令改变为交互式 shell:
|
||||
|
||||
```
|
||||
kubectl debug myapp -it --copy-to=myapp-debug --container=myapp -- sh
|
||||
```
|
||||
|
||||
```
|
||||
If you don't see a command prompt, try pressing enter.
|
||||
/ #
|
||||
```
|
||||
|
||||
<!--
|
||||
Now you have an interactive shell that you can use to perform tasks like
|
||||
checking filesystem paths or running the container command manually.
|
||||
-->
|
||||
现在你有了一个可以执行类似检查文件系统路径或者手动运行容器命令的交互式 shell。
|
||||
|
||||
<!--
|
||||
* To change the command of a specific container you must
|
||||
specify its name using `--container` or `kubectl debug` will instead
|
||||
create a new container to run the command you specified.
|
||||
* The `-i` flag causes `kubectl debug` to attach to the container by default.
|
||||
You can prevent this by specifying `--attach=false`. If your session becomes
|
||||
disconnected you can reattach using `kubectl attach`.
|
||||
-->
|
||||
{{< note >}}
|
||||
* 要更改指定容器的命令,你必须用 `--container` 命令指定容器的名字,
|
||||
否则 `kubectl debug` 将建立一个新的容器运行你指定的命令。
|
||||
* 默认情况下,标志 `-i` 使 `kubectl debug` 附加到容器。
|
||||
你可通过指定 `--attach=false` 来防止这种情况。
|
||||
如果你的断开连接,可以使用 `kubectl attach` 重新连接。
|
||||
{{< /note >}}
|
||||
|
||||
<!--
|
||||
Don't forget to clean up the debugging Pod when you're finished with it:
|
||||
-->
|
||||
不要忘了清理调试 Pod:
|
||||
|
||||
```shell
|
||||
kubectl delete pod myapp myapp-debug
|
||||
```
|
||||
<!--
|
||||
### Copying a Pod while changing container images
|
||||
|
||||
In some situations you may want to change a misbehaving Pod from its normal
|
||||
production container images to an image containing a debugging build or
|
||||
additional utilities.
|
||||
|
||||
As an example, create a Pod using `kubectl run`:
|
||||
-->
|
||||
### 在更改容器镜像时创建 Pod 副本
|
||||
|
||||
在某些情况下,你可能想从正常生产容器镜像中
|
||||
把行为异常的 Pod 改变为包含调试版本或者附加应用的镜像。
|
||||
|
||||
下面的例子,用 `kubectl run`创建一个 Pod:
|
||||
|
||||
```
|
||||
kubectl run myapp --image=busybox:1.28 --restart=Never -- sleep 1d
|
||||
```
|
||||
<!--
|
||||
Now use `kubectl debug` to make a copy and change its container image
|
||||
to `ubuntu`:
|
||||
-->
|
||||
现在可以使用 `kubectl debug` 创建一个副本
|
||||
并改变容器镜像为 `ubuntu`:
|
||||
|
||||
```
|
||||
kubectl debug myapp --copy-to=myapp-debug --set-image=*=ubuntu
|
||||
```
|
||||
|
||||
<!--
|
||||
The syntax of `--set-image` uses the same `container_name=image` syntax as
|
||||
`kubectl set image`. `*=ubuntu` means change the image of all containers
|
||||
to `ubuntu`.
|
||||
|
||||
Don't forget to clean up the debugging Pod when you're finished with it:
|
||||
-->
|
||||
`--set-image` 与 `container_name=image` 使用相同的 `kubectl set image` 语法。
|
||||
`*=ubuntu` 表示把所有容器的镜像改为 `ubuntu`。
|
||||
|
||||
```shell
|
||||
kubectl delete pod myapp myapp-debug
|
||||
```
|
||||
|
||||
<!--
|
||||
## Debugging via a shell on the node {#node-shell-session}
|
||||
|
||||
If none of these approaches work, you can find the Node on which the Pod is
|
||||
running and create a privileged Pod running in the host namespaces. To create
|
||||
an interactive shell on a node using `kubectl debug`, run:
|
||||
-->
|
||||
## 在节点上通过 shell 来进行调试 {#node-shell-session}
|
||||
|
||||
如果这些方法都不起作用,你可以找到运行 Pod 的节点,然后在节点上部署一个运行在宿主名字空间的特权 Pod。
|
||||
|
||||
你可以通过`kubectl debug` 在节点上创建一个交互式 shell:
|
||||
|
||||
```shell
|
||||
kubectl debug node/mynode -it --image=ubuntu
|
||||
```
|
||||
|
||||
```
|
||||
Creating debugging pod node-debugger-mynode-pdx84 with container debugger on node mynode.
|
||||
If you don't see a command prompt, try pressing enter.
|
||||
root@ek8s:/#
|
||||
```
|
||||
|
||||
<!--
|
||||
When creating a debugging session on a node, keep in mind that:
|
||||
|
||||
* `kubectl debug` automatically generates the name of the new Pod based on
|
||||
the name of the Node.
|
||||
* The container runs in the host IPC, Network, and PID namespaces.
|
||||
* The root filesystem of the Node will be mounted at `/host`.
|
||||
|
||||
Don't forget to clean up the debugging Pod when you're finished with it:
|
||||
-->
|
||||
当在节点上创建调试会话,注意以下要点:
|
||||
* `kubectl debug` 基于节点的名字自动生成新的 Pod 的名字。
|
||||
* 新的调试容器运行在宿主命名空间里(IPC, 网络 还有PID命名空间)。
|
||||
* 节点的根文件系统会被挂载在 `/host`。
|
||||
|
||||
当你完成节点调试时,不要忘记清理调试 Pod:
|
||||
|
||||
```shell
|
||||
kubectl delete pod node-debugger-mynode-pdx84
|
||||
```
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,71 @@
|
||||
---
|
||||
title: 调试 StatefulSet
|
||||
content_type: task
|
||||
weight: 30
|
||||
---
|
||||
<!--
|
||||
reviewers:
|
||||
- bprashanth
|
||||
- enisoc
|
||||
- erictune
|
||||
- foxish
|
||||
- janetkuo
|
||||
- kow3ns
|
||||
- smarterclayton
|
||||
title: Debug a StatefulSet
|
||||
content_type: task
|
||||
weight: 30
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
<!--
|
||||
This task shows you how to debug a StatefulSet.
|
||||
-->
|
||||
此任务展示如何调试 StatefulSet。
|
||||
|
||||
## {{% heading "prerequisites" %}}
|
||||
|
||||
<!--
|
||||
* You need to have a Kubernetes cluster, and the kubectl command-line tool must be configured to communicate with your cluster.
|
||||
* You should have a StatefulSet running that you want to investigate.
|
||||
-->
|
||||
* 你需要有一个 Kubernetes 集群,已配置好的 kubectl 命令行工具与你的集群进行通信。
|
||||
* 你应该有一个运行中的 StatefulSet,以便用于调试。
|
||||
|
||||
<!-- steps -->
|
||||
|
||||
<!--
|
||||
## Debugging a StatefulSet
|
||||
|
||||
In order to list all the pods which belong to a StatefulSet, which have a label `app=myapp` set on them,
|
||||
you can use the following:
|
||||
-->
|
||||
## 调试 StatefulSet {#debuggin-a-statefulset}
|
||||
|
||||
StatefulSet 在创建 Pod 时为其设置了 `app=myapp` 标签,列出仅属于某 StatefulSet
|
||||
的所有 Pod 时,可以使用以下命令:
|
||||
|
||||
```shell
|
||||
kubectl get pods -l app=myapp
|
||||
```
|
||||
|
||||
<!--
|
||||
If you find that any Pods listed are in `Unknown` or `Terminating` state for an extended period of time,
|
||||
refer to the [Deleting StatefulSet Pods](/docs/tasks/run-application/delete-stateful-set/) task for
|
||||
instructions on how to deal with them.
|
||||
You can debug individual Pods in a StatefulSet using the
|
||||
[Debugging Pods](/docs/tasks/debug/debug-application/debug-pods/) guide.
|
||||
-->
|
||||
如果你发现列出的任何 Pod 长时间处于 `Unknown` 或 `Terminating` 状态,请参阅
|
||||
[删除 StatefulSet Pod](/zh/docs/tasks/run-application/delete-stateful-set/)
|
||||
了解如何处理它们的说明。
|
||||
你可以参考[调试 Pod](/zh/docs/tasks/debug/debug-application/debug-pods/)
|
||||
来调试 StatefulSet 中的各个 Pod。
|
||||
|
||||
## {{% heading "whatsnext" %}}
|
||||
|
||||
<!--
|
||||
Learn more about [debugging an init-container](/docs/tasks/debug/debug-application/debug-init-containers/).
|
||||
-->
|
||||
* 进一步了解如何[调试 Init 容器](/zh/docs/tasks/debug/debug-application/debug-init-containers/)。
|
||||
|
||||
@@ -0,0 +1,174 @@
|
||||
---
|
||||
title: 确定 Pod 失败的原因
|
||||
content_type: task
|
||||
---
|
||||
|
||||
<!--
|
||||
title: Determine the Reason for Pod Failure
|
||||
content_type: task
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
<!--
|
||||
This page shows how to write and read a Container
|
||||
termination message.
|
||||
-->
|
||||
本文介绍如何编写和读取容器的终止消息。
|
||||
|
||||
<!--
|
||||
Termination messages provide a way for containers to write
|
||||
information about fatal events to a location where it can
|
||||
be easily retrieved and surfaced by tools like dashboards
|
||||
and monitoring software. In most cases, information that you
|
||||
put in a termination message should also be written to
|
||||
the general
|
||||
[Kubernetes logs](/docs/concepts/cluster-administration/logging/).
|
||||
-->
|
||||
终止消息为容器提供了一种方法,可以将有关致命事件的信息写入某个位置,
|
||||
在该位置可以通过仪表板和监控软件等工具轻松检索和显示致命事件。
|
||||
在大多数情况下,你放入终止消息中的信息也应该写入
|
||||
[常规 Kubernetes 日志](/zh/docs/concepts/cluster-administration/logging/)。
|
||||
|
||||
## {{% heading "prerequisites" %}}
|
||||
|
||||
{{< include "task-tutorial-prereqs.md" >}} {{< version-check >}}
|
||||
|
||||
<!-- steps -->
|
||||
|
||||
<!--
|
||||
## Writing and reading a termination message
|
||||
|
||||
In this exercise, you create a Pod that runs one container.
|
||||
The configuration file specifies a command that runs when
|
||||
the container starts.
|
||||
-->
|
||||
## 读写终止消息
|
||||
|
||||
在本练习中,你将创建运行一个容器的 Pod。
|
||||
配置文件指定在容器启动时要运行的命令。
|
||||
|
||||
{{< codenew file="debug/termination.yaml" >}}
|
||||
|
||||
<!-- 1. Create a Pod based on the YAML configuration file: -->
|
||||
1. 基于 YAML 配置文件创建 Pod:
|
||||
|
||||
kubectl apply -f https://k8s.io/examples/debug/termination.yaml
|
||||
|
||||
<!--
|
||||
In the YAML file, in the `command` and `args` fields, you can see that the
|
||||
container sleeps for 10 seconds and then writes "Sleep expired" to
|
||||
the `/dev/termination-log` file. After the container writes
|
||||
the "Sleep expired" message, it terminates.
|
||||
-->
|
||||
YAML 文件中,在 `command` 和 `args` 字段,你可以看到容器休眠 10 秒然后将 "Sleep expired"
|
||||
写入 `/dev/termination-log` 文件。
|
||||
容器写完 "Sleep expired" 消息后就终止了。
|
||||
|
||||
<!-- 1. Display information about the Pod: -->
|
||||
1. 显示 Pod 的信息:
|
||||
|
||||
kubectl get pod termination-demo
|
||||
|
||||
<!--Repeat the preceding command until the Pod is no longer running.-->
|
||||
重复前面的命令直到 Pod 不再运行。
|
||||
|
||||
<!-- 1. Display detailed information about the Pod: -->
|
||||
1. 显示 Pod 的详细信息:
|
||||
|
||||
kubectl get pod termination-demo --output=yaml
|
||||
|
||||
<!--The output includes the "Sleep expired" message:-->
|
||||
输出结果包含 "Sleep expired" 消息:
|
||||
|
||||
apiVersion: v1
|
||||
kind: Pod
|
||||
...
|
||||
lastState:
|
||||
terminated:
|
||||
containerID: ...
|
||||
exitCode: 0
|
||||
finishedAt: ...
|
||||
message: |
|
||||
Sleep expired
|
||||
...
|
||||
|
||||
<!--
|
||||
1. Use a Go template to filter the output so that it includes
|
||||
only the termination message:
|
||||
-->
|
||||
1. 使用 Go 模板过滤输出结果,使其只含有终止消息:
|
||||
|
||||
kubectl get pod termination-demo -o go-template="{{range .status.containerStatuses}}{{.lastState.terminated.message}}{{end}}"
|
||||
|
||||
<!--
|
||||
If you are running a multi-container pod, you can use a Go template to include the container's name. By doing so, you can discover which of the containers is failing:
|
||||
-->
|
||||
如果你正在运行多容器 Pod,则可以使用 Go 模板来包含容器的名称。这样,你可以发现哪些容器出现故障:
|
||||
|
||||
```shell
|
||||
kubectl get pod multi-container-pod -o go-template='{{range .status.containerStatuses}}{{printf "%s:\n%s\n\n" .name .lastState.terminated.message}}{{end}}'
|
||||
```
|
||||
|
||||
<!--
|
||||
## Customizing the termination message
|
||||
|
||||
Kubernetes retrieves termination messages from the termination message file
|
||||
specified in the `terminationMessagePath` field of a Container, which as a default
|
||||
value of `/dev/termination-log`. By customizing this field, you can tell Kubernetes
|
||||
to use a different file. Kubernetes use the contents from the specified file to
|
||||
populate the Container's status message on both success and failure.
|
||||
-->
|
||||
## 定制终止消息
|
||||
|
||||
Kubernetes 从容器的 `terminationMessagePath` 字段中指定的终止消息文件中检索终止消息,
|
||||
默认值为 `/dev/termination-log`。
|
||||
通过定制这个字段,你可以告诉 Kubernetes 使用不同的文件。
|
||||
Kubernetes 使用指定文件中的内容在成功和失败时填充容器的状态消息。
|
||||
|
||||
<!--
|
||||
In the following example, the container writes termination messages to
|
||||
`/tmp/my-log` for Kubernetes to retrieve:
|
||||
-->
|
||||
在下例中,容器将终止消息写入 `/tmp/my-log` 给 Kubernetes 来接收:
|
||||
|
||||
```yaml
|
||||
apiVersion: v1
|
||||
kind: Pod
|
||||
metadata:
|
||||
name: msg-path-demo
|
||||
spec:
|
||||
containers:
|
||||
- name: msg-path-demo-container
|
||||
image: debian
|
||||
terminationMessagePath: "/tmp/my-log"
|
||||
```
|
||||
|
||||
<!--
|
||||
Moreover, users can set the `terminationMessagePolicy` field of a Container for
|
||||
further customization. This field defaults to "`File`" which means the termination
|
||||
messages are retrieved only from the termination message file. By setting the
|
||||
`terminationMessagePolicy` to "`FallbackToLogsOnError`", you can tell Kubernetes
|
||||
to use the last chunk of container log output if the termination message file
|
||||
is empty and the container exited with an error. The log output is limited to
|
||||
2048 bytes or 80 lines, whichever is smaller.
|
||||
-->
|
||||
此外,用户可以设置容器的 `terminationMessagePolicy` 字段,以便进一步自定义。
|
||||
此字段默认为 "`File`",这意味着仅从终止消息文件中检索终止消息。
|
||||
通过将 `terminationMessagePolicy` 设置为 "`FallbackToLogsOnError`",你就可以告诉 Kubernetes,在容器因错误退出时,如果终止消息文件为空,则使用容器日志输出的最后一块作为终止消息。
|
||||
日志输出限制为 2048 字节或 80 行,以较小者为准。
|
||||
|
||||
## {{% heading "whatsnext" %}}
|
||||
|
||||
<!--
|
||||
* See the `terminationMessagePath` field in
|
||||
[Container](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#container-v1-core).
|
||||
* Learn about [retrieving logs](/docs/concepts/cluster-administration/logging/).
|
||||
* Learn about [Go templates](https://golang.org/pkg/text/template/).
|
||||
-->
|
||||
|
||||
* 参考 [Container](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#container-v1-core)
|
||||
资源的 `terminationMessagePath` 字段。
|
||||
* 了解[接收日志](/zh/docs/concepts/cluster-administration/logging/)。
|
||||
* 了解 [Go 模版](https://golang.org/pkg/text/template/)。
|
||||
|
||||
@@ -0,0 +1,193 @@
|
||||
---
|
||||
title: 获取正在运行容器的 Shell
|
||||
content_type: task
|
||||
---
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
<!--
|
||||
This page shows how to use `kubectl exec` to get a shell to a
|
||||
running Container.
|
||||
-->
|
||||
本文介绍怎样使用 `kubectl exec` 命令获取正在运行容器的 Shell。
|
||||
|
||||
## {{% heading "prerequisites" %}}
|
||||
|
||||
{{< include "task-tutorial-prereqs.md" >}} {{< version-check >}}
|
||||
|
||||
<!-- steps -->
|
||||
|
||||
<!--
|
||||
## Getting a shell to a Container
|
||||
-->
|
||||
## 获取容器的 Shell
|
||||
|
||||
<!--
|
||||
In this exercise, you create a Pod that has one Container. The Container
|
||||
runs the nginx image. Here is the configuration file for the Pod:
|
||||
-->
|
||||
在本练习中,你将创建包含一个容器的 Pod。容器运行 nginx 镜像。下面是 Pod 的配置文件:
|
||||
|
||||
{{< codenew file="application/shell-demo.yaml" >}}
|
||||
|
||||
<!--
|
||||
Create the Pod:
|
||||
-->
|
||||
创建 Pod:
|
||||
|
||||
```shell
|
||||
kubectl create -f https://k8s.io/examples/application/shell-demo.yaml
|
||||
```
|
||||
|
||||
<!--
|
||||
Verify that the Container is running:
|
||||
-->
|
||||
检查容器是否运行正常:
|
||||
|
||||
```shell
|
||||
kubectl get pod shell-demo
|
||||
```
|
||||
|
||||
<!--
|
||||
Get a shell to the running Container:
|
||||
-->
|
||||
获取正在运行容器的 Shell:
|
||||
|
||||
```shell
|
||||
kubectl exec -it shell-demo -- /bin/bash
|
||||
```
|
||||
{{< note >}}
|
||||
|
||||
<!--
|
||||
The double dash symbol "--" is used to separate the arguments you want to pass to the command from the kubectl arguments.
|
||||
-->
|
||||
双破折号 "--" 用于将要传递给命令的参数与 kubectl 的参数分开。
|
||||
{{< /note >}}
|
||||
|
||||
<!--
|
||||
In your shell, list the root directory:
|
||||
-->
|
||||
在 shell 中,打印根目录:
|
||||
|
||||
```shell
|
||||
root@shell-demo:/# ls /
|
||||
```
|
||||
|
||||
<!--
|
||||
In your shell, experiment with other commands. Here are
|
||||
some examples:
|
||||
-->
|
||||
在 shell 中,实验其他命令。下面是一些示例:
|
||||
|
||||
```shell
|
||||
root@shell-demo:/# ls /
|
||||
root@shell-demo:/# cat /proc/mounts
|
||||
root@shell-demo:/# cat /proc/1/maps
|
||||
root@shell-demo:/# apt-get update
|
||||
root@shell-demo:/# apt-get install -y tcpdump
|
||||
root@shell-demo:/# tcpdump
|
||||
root@shell-demo:/# apt-get install -y lsof
|
||||
root@shell-demo:/# lsof
|
||||
root@shell-demo:/# apt-get install -y procps
|
||||
root@shell-demo:/# ps aux
|
||||
root@shell-demo:/# ps aux | grep nginx
|
||||
```
|
||||
|
||||
<!--
|
||||
## Writing the root page for nginx
|
||||
-->
|
||||
## 编写 nginx 的根页面
|
||||
|
||||
<!--
|
||||
Look again at the configuration file for your Pod. The Pod
|
||||
has an `emptyDir` volume, and the Container mounts the volume
|
||||
at `/usr/share/nginx/html`.
|
||||
-->
|
||||
再看一下 Pod 的配置文件。该 Pod 有个 `emptyDir` 卷,容器将该卷挂载到了 `/usr/share/nginx/html`。
|
||||
|
||||
<!--
|
||||
In your shell, create an `index.html` file in the `/usr/share/nginx/html`
|
||||
directory:
|
||||
-->
|
||||
在 shell 中,在 `/usr/share/nginx/html` 目录创建一个 `index.html` 文件:
|
||||
|
||||
```shell
|
||||
root@shell-demo:/# echo Hello shell demo > /usr/share/nginx/html/index.html
|
||||
```
|
||||
|
||||
<!--
|
||||
In your shell, send a GET request to the nginx server:
|
||||
-->
|
||||
在 shell 中,向 nginx 服务器发送 GET 请求:
|
||||
|
||||
```shell
|
||||
root@shell-demo:/# apt-get update
|
||||
root@shell-demo:/# apt-get install curl
|
||||
root@shell-demo:/# curl localhost
|
||||
```
|
||||
|
||||
<!--
|
||||
The output shows the text that you wrote to the `index.html` file:
|
||||
-->
|
||||
输出结果显示了你在 `index.html` 中写入的文本。
|
||||
|
||||
```shell
|
||||
Hello shell demo
|
||||
```
|
||||
|
||||
<!--
|
||||
When you are finished with your shell, enter `exit`.
|
||||
-->
|
||||
当用完 shell 后,输入 `exit` 退出。
|
||||
|
||||
<!--
|
||||
## Running individual commands in a Container
|
||||
-->
|
||||
## 在容器中运行单个命令
|
||||
|
||||
<!--
|
||||
In an ordinary command window, not your shell, list the environment
|
||||
variables in the running Container:
|
||||
-->
|
||||
在普通的命令窗口(而不是 shell)中,打印环境运行容器中的变量:
|
||||
|
||||
```shell
|
||||
kubectl exec shell-demo env
|
||||
```
|
||||
|
||||
<!--
|
||||
Experiment running other commands. Here are some examples:
|
||||
-->
|
||||
实验运行其他命令。下面是一些示例:
|
||||
|
||||
```shell
|
||||
kubectl exec shell-demo ps aux
|
||||
kubectl exec shell-demo ls /
|
||||
kubectl exec shell-demo cat /proc/1/mounts
|
||||
```
|
||||
|
||||
<!-- discussion -->
|
||||
|
||||
<!--
|
||||
## Opening a shell when a Pod has more than one Container
|
||||
-->
|
||||
## 当 Pod 包含多个容器时打开 shell
|
||||
|
||||
<!--
|
||||
If a Pod has more than one Container, use `--container` or `-c` to
|
||||
specify a Container in the `kubectl exec` command. For example,
|
||||
suppose you have a Pod named my-pod, and the Pod has two containers
|
||||
named main-app and helper-app. The following command would open a
|
||||
shell to the main-app Container.
|
||||
-->
|
||||
如果 Pod 有多个容器,`--container` 或者 `-c` 可以在 `kubectl exec` 命令中指定容器。
|
||||
例如,你有个名为 my-pod 的 Pod,该 Pod 有两个容器分别为 main-app 和 healper-app。
|
||||
下面的命令将会打开一个 shell 访问 main-app 容器。
|
||||
|
||||
```shell
|
||||
kubectl exec -it my-pod --container main-app -- /bin/bash
|
||||
```
|
||||
|
||||
## {{% heading "whatsnext" %}}
|
||||
|
||||
* [kubectl exec](/docs/reference/generated/kubectl/kubectl-commands/#exec)
|
||||
@@ -0,0 +1,459 @@
|
||||
---
|
||||
title: 集群故障排查
|
||||
description: 调试常见的集群问题。
|
||||
weight: 20
|
||||
no_list: true
|
||||
---
|
||||
<!--
|
||||
reviewers:
|
||||
- davidopp
|
||||
title: "Troubleshooting Clusters"
|
||||
description: Debugging common cluster issues.
|
||||
weight: 20
|
||||
no_list: true
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
<!--
|
||||
This doc is about cluster troubleshooting; we assume you have already ruled out your application as the root cause of the
|
||||
problem you are experiencing. See
|
||||
the [application troubleshooting guide](/docs/tasks/debug/debug-application/) for tips on application debugging.
|
||||
You may also visit the [troubleshooting overview document](/docs/tasks/debug/) for more information.
|
||||
-->
|
||||
本篇文档是介绍集群故障排查的;我们假设对于你碰到的问题,你已经排除了是由应用程序造成的。
|
||||
对于应用的调试,请参阅[应用故障排查指南](/zh/docs/tasks/debug/debug-application/)。
|
||||
你也可以访问[故障排查](/zh/docs/tasks/debug/)来获取更多的信息。
|
||||
|
||||
<!-- body -->
|
||||
|
||||
<!--
|
||||
## Listing your cluster
|
||||
|
||||
The first thing to debug in your cluster is if your nodes are all registered correctly.
|
||||
|
||||
Run the following command:
|
||||
-->
|
||||
## 列举集群节点 {#listing-your-cluster}
|
||||
|
||||
调试的第一步是查看所有的节点是否都已正确注册。
|
||||
|
||||
运行以下命令:
|
||||
|
||||
```shell
|
||||
kubectl get nodes
|
||||
```
|
||||
|
||||
<!--
|
||||
And verify that all of the nodes you expect to see are present and that they are all in the `Ready` state.
|
||||
|
||||
To get detailed information about the overall health of your cluster, you can run:
|
||||
-->
|
||||
验证你所希望看见的所有节点都能够显示出来,并且都处于 `Ready` 状态。
|
||||
|
||||
为了了解你的集群的总体健康状况详情,你可以运行:
|
||||
|
||||
```shell
|
||||
kubectl cluster-info dump
|
||||
```
|
||||
|
||||
<!--
|
||||
### Example: debugging a down/unreachable node
|
||||
|
||||
Sometimes when debugging it can be useful to look at the status of a node -- for example, because you've noticed strange behavior of a Pod that's running on the node, or to find out why a Pod won't schedule onto the node. As with Pods, you can use `kubectl describe node` and `kubectl get node -o yaml` to retrieve detailed information about nodes. For example, here's what you'll see if a node is down (disconnected from the network, or kubelet dies and won't restart, etc.). Notice the events that show the node is NotReady, and also notice that the pods are no longer running (they are evicted after five minutes of NotReady status).
|
||||
-->
|
||||
### 示例:调试关闭/无法访问的节点 {#example-debugging-a-down-unreachable-node}
|
||||
|
||||
有时在调试时查看节点的状态很有用——例如,因为你注意到在节点上运行的 Pod 的奇怪行为,
|
||||
或者找出为什么 Pod 不会调度到节点上。与 Pod 一样,你可以使用 `kubectl describe node`
|
||||
和 `kubectl get node -o yaml` 来检索有关节点的详细信息。
|
||||
例如,如果节点关闭(与网络断开连接,或者 kubelet 进程挂起并且不会重新启动等),
|
||||
你将看到以下内容。请注意显示节点为 NotReady 的事件,并注意 Pod 不再运行(它们在 NotReady 状态五分钟后被驱逐)。
|
||||
|
||||
```shell
|
||||
kubectl get nodes
|
||||
```
|
||||
|
||||
```none
|
||||
NAME STATUS ROLES AGE VERSION
|
||||
kube-worker-1 NotReady <none> 1h v1.23.3
|
||||
kubernetes-node-bols Ready <none> 1h v1.23.3
|
||||
kubernetes-node-st6x Ready <none> 1h v1.23.3
|
||||
kubernetes-node-unaj Ready <none> 1h v1.23.3
|
||||
```
|
||||
|
||||
```shell
|
||||
kubectl describe node kube-worker-1
|
||||
```
|
||||
|
||||
```none
|
||||
Name: kube-worker-1
|
||||
Roles: <none>
|
||||
Labels: beta.kubernetes.io/arch=amd64
|
||||
beta.kubernetes.io/os=linux
|
||||
kubernetes.io/arch=amd64
|
||||
kubernetes.io/hostname=kube-worker-1
|
||||
kubernetes.io/os=linux
|
||||
Annotations: kubeadm.alpha.kubernetes.io/cri-socket: /run/containerd/containerd.sock
|
||||
node.alpha.kubernetes.io/ttl: 0
|
||||
volumes.kubernetes.io/controller-managed-attach-detach: true
|
||||
CreationTimestamp: Thu, 17 Feb 2022 16:46:30 -0500
|
||||
Taints: node.kubernetes.io/unreachable:NoExecute
|
||||
node.kubernetes.io/unreachable:NoSchedule
|
||||
Unschedulable: false
|
||||
Lease:
|
||||
HolderIdentity: kube-worker-1
|
||||
AcquireTime: <unset>
|
||||
RenewTime: Thu, 17 Feb 2022 17:13:09 -0500
|
||||
Conditions:
|
||||
Type Status LastHeartbeatTime LastTransitionTime Reason Message
|
||||
---- ------ ----------------- ------------------ ------ -------
|
||||
NetworkUnavailable False Thu, 17 Feb 2022 17:09:13 -0500 Thu, 17 Feb 2022 17:09:13 -0500 WeaveIsUp Weave pod has set this
|
||||
MemoryPressure Unknown Thu, 17 Feb 2022 17:12:40 -0500 Thu, 17 Feb 2022 17:13:52 -0500 NodeStatusUnknown Kubelet stopped posting node status.
|
||||
DiskPressure Unknown Thu, 17 Feb 2022 17:12:40 -0500 Thu, 17 Feb 2022 17:13:52 -0500 NodeStatusUnknown Kubelet stopped posting node status.
|
||||
PIDPressure Unknown Thu, 17 Feb 2022 17:12:40 -0500 Thu, 17 Feb 2022 17:13:52 -0500 NodeStatusUnknown Kubelet stopped posting node status.
|
||||
Ready Unknown Thu, 17 Feb 2022 17:12:40 -0500 Thu, 17 Feb 2022 17:13:52 -0500 NodeStatusUnknown Kubelet stopped posting node status.
|
||||
Addresses:
|
||||
InternalIP: 192.168.0.113
|
||||
Hostname: kube-worker-1
|
||||
Capacity:
|
||||
cpu: 2
|
||||
ephemeral-storage: 15372232Ki
|
||||
hugepages-2Mi: 0
|
||||
memory: 2025188Ki
|
||||
pods: 110
|
||||
Allocatable:
|
||||
cpu: 2
|
||||
ephemeral-storage: 14167048988
|
||||
hugepages-2Mi: 0
|
||||
memory: 1922788Ki
|
||||
pods: 110
|
||||
System Info:
|
||||
Machine ID: 9384e2927f544209b5d7b67474bbf92b
|
||||
System UUID: aa829ca9-73d7-064d-9019-df07404ad448
|
||||
Boot ID: 5a295a03-aaca-4340-af20-1327fa5dab5c
|
||||
Kernel Version: 5.13.0-28-generic
|
||||
OS Image: Ubuntu 21.10
|
||||
Operating System: linux
|
||||
Architecture: amd64
|
||||
Container Runtime Version: containerd://1.5.9
|
||||
Kubelet Version: v1.23.3
|
||||
Kube-Proxy Version: v1.23.3
|
||||
Non-terminated Pods: (4 in total)
|
||||
Namespace Name CPU Requests CPU Limits Memory Requests Memory Limits Age
|
||||
--------- ---- ------------ ---------- --------------- ------------- ---
|
||||
default nginx-deployment-67d4bdd6f5-cx2nz 500m (25%) 500m (25%) 128Mi (6%) 128Mi (6%) 23m
|
||||
default nginx-deployment-67d4bdd6f5-w6kd7 500m (25%) 500m (25%) 128Mi (6%) 128Mi (6%) 23m
|
||||
kube-system kube-proxy-dnxbz 0 (0%) 0 (0%) 0 (0%) 0 (0%) 28m
|
||||
kube-system weave-net-gjxxp 100m (5%) 0 (0%) 200Mi (10%) 0 (0%) 28m
|
||||
Allocated resources:
|
||||
(Total limits may be over 100 percent, i.e., overcommitted.)
|
||||
Resource Requests Limits
|
||||
-------- -------- ------
|
||||
cpu 1100m (55%) 1 (50%)
|
||||
memory 456Mi (24%) 256Mi (13%)
|
||||
ephemeral-storage 0 (0%) 0 (0%)
|
||||
hugepages-2Mi 0 (0%) 0 (0%)
|
||||
Events:
|
||||
...
|
||||
```
|
||||
|
||||
```shell
|
||||
kubectl get node kube-worker-1 -o yaml
|
||||
```
|
||||
|
||||
```yaml
|
||||
apiVersion: v1
|
||||
kind: Node
|
||||
metadata:
|
||||
annotations:
|
||||
kubeadm.alpha.kubernetes.io/cri-socket: /run/containerd/containerd.sock
|
||||
node.alpha.kubernetes.io/ttl: "0"
|
||||
volumes.kubernetes.io/controller-managed-attach-detach: "true"
|
||||
creationTimestamp: "2022-02-17T21:46:30Z"
|
||||
labels:
|
||||
beta.kubernetes.io/arch: amd64
|
||||
beta.kubernetes.io/os: linux
|
||||
kubernetes.io/arch: amd64
|
||||
kubernetes.io/hostname: kube-worker-1
|
||||
kubernetes.io/os: linux
|
||||
name: kube-worker-1
|
||||
resourceVersion: "4026"
|
||||
uid: 98efe7cb-2978-4a0b-842a-1a7bf12c05f8
|
||||
spec: {}
|
||||
status:
|
||||
addresses:
|
||||
- address: 192.168.0.113
|
||||
type: InternalIP
|
||||
- address: kube-worker-1
|
||||
type: Hostname
|
||||
allocatable:
|
||||
cpu: "2"
|
||||
ephemeral-storage: "14167048988"
|
||||
hugepages-2Mi: "0"
|
||||
memory: 1922788Ki
|
||||
pods: "110"
|
||||
capacity:
|
||||
cpu: "2"
|
||||
ephemeral-storage: 15372232Ki
|
||||
hugepages-2Mi: "0"
|
||||
memory: 2025188Ki
|
||||
pods: "110"
|
||||
conditions:
|
||||
- lastHeartbeatTime: "2022-02-17T22:20:32Z"
|
||||
lastTransitionTime: "2022-02-17T22:20:32Z"
|
||||
message: Weave pod has set this
|
||||
reason: WeaveIsUp
|
||||
status: "False"
|
||||
type: NetworkUnavailable
|
||||
- lastHeartbeatTime: "2022-02-17T22:20:15Z"
|
||||
lastTransitionTime: "2022-02-17T22:13:25Z"
|
||||
message: kubelet has sufficient memory available
|
||||
reason: KubeletHasSufficientMemory
|
||||
status: "False"
|
||||
type: MemoryPressure
|
||||
- lastHeartbeatTime: "2022-02-17T22:20:15Z"
|
||||
lastTransitionTime: "2022-02-17T22:13:25Z"
|
||||
message: kubelet has no disk pressure
|
||||
reason: KubeletHasNoDiskPressure
|
||||
status: "False"
|
||||
type: DiskPressure
|
||||
- lastHeartbeatTime: "2022-02-17T22:20:15Z"
|
||||
lastTransitionTime: "2022-02-17T22:13:25Z"
|
||||
message: kubelet has sufficient PID available
|
||||
reason: KubeletHasSufficientPID
|
||||
status: "False"
|
||||
type: PIDPressure
|
||||
- lastHeartbeatTime: "2022-02-17T22:20:15Z"
|
||||
lastTransitionTime: "2022-02-17T22:15:15Z"
|
||||
message: kubelet is posting ready status. AppArmor enabled
|
||||
reason: KubeletReady
|
||||
status: "True"
|
||||
type: Ready
|
||||
daemonEndpoints:
|
||||
kubeletEndpoint:
|
||||
Port: 10250
|
||||
nodeInfo:
|
||||
architecture: amd64
|
||||
bootID: 22333234-7a6b-44d4-9ce1-67e31dc7e369
|
||||
containerRuntimeVersion: containerd://1.5.9
|
||||
kernelVersion: 5.13.0-28-generic
|
||||
kubeProxyVersion: v1.23.3
|
||||
kubeletVersion: v1.23.3
|
||||
machineID: 9384e2927f544209b5d7b67474bbf92b
|
||||
operatingSystem: linux
|
||||
osImage: Ubuntu 21.10
|
||||
systemUUID: aa829ca9-73d7-064d-9019-df07404ad448
|
||||
```
|
||||
|
||||
<!--
|
||||
## Looking at logs
|
||||
|
||||
For now, digging deeper into the cluster requires logging into the relevant machines. Here are the locations
|
||||
of the relevant log files. On systemd-based systems, you may need to use `journalctl` instead of examining log files.
|
||||
-->
|
||||
## 查看日志 {#looking-at-logs}
|
||||
|
||||
目前,深入挖掘集群需要登录相关机器。以下是相关日志文件的位置。
|
||||
在基于 systemd 的系统上,你可能需要使用 `journalctl` 而不是检查日志文件。
|
||||
|
||||
<!--
|
||||
### Control Plane nodes
|
||||
|
||||
* `/var/log/kube-apiserver.log` - API Server, responsible for serving the API
|
||||
* `/var/log/kube-scheduler.log` - Scheduler, responsible for making scheduling decisions
|
||||
* `/var/log/kube-controller-manager.log` - a component that runs most Kubernetes built-in {{<glossary_tooltip text="controllers" term_id="controller">}}, with the notable exception of scheduling (the kube-scheduler handles scheduling).
|
||||
-->
|
||||
### 控制平面节点 {#control-plane-nodes}
|
||||
|
||||
* `/var/log/kube-apiserver.log` —— API 服务器 API
|
||||
* `/var/log/kube-scheduler.log` —— 调度器,负责制定调度决策
|
||||
* `/var/log/kube-controller-manager.log` —— 运行大多数 Kubernetes
|
||||
内置{{<glossary_tooltip text="控制器" term_id="controller">}}的组件,除了调度(kube-scheduler 处理调度)。
|
||||
|
||||
<!--
|
||||
### Worker Nodes
|
||||
|
||||
* `/var/log/kubelet.log` - logs from the kubelet, responsible for running containers on the node
|
||||
* `/var/log/kube-proxy.log` - logs from `kube-proxy`, which is responsible for directing traffic to Service endpoints
|
||||
-->
|
||||
|
||||
### 工作节点 {#worker-nodes}
|
||||
|
||||
* `/var/log/kubelet.log` —— 来自 `kubelet` 的日志,负责在节点运行容器
|
||||
* `/var/log/kube-proxy.log` —— 来自 `kube-proxy` 的日志,负责将流量转发到服务端点
|
||||
|
||||
<!--
|
||||
## Cluster failure modes
|
||||
|
||||
This is an incomplete list of things that could go wrong, and how to adjust your cluster setup to mitigate the problems.
|
||||
-->
|
||||
## 集群故障模式 {#cluster-failure-modes}
|
||||
|
||||
这是可能出错的事情的不完整列表,以及如何调整集群设置以缓解问题。
|
||||
|
||||
<!--
|
||||
### Contributing causes
|
||||
|
||||
- VM(s) shutdown
|
||||
- Network partition within cluster, or between cluster and users
|
||||
- Crashes in Kubernetes software
|
||||
- Data loss or unavailability of persistent storage (e.g. GCE PD or AWS EBS volume)
|
||||
- Operator error, for example misconfigured Kubernetes software or application software
|
||||
-->
|
||||
### 造成原因 {#contributing-causes}
|
||||
|
||||
- 虚拟机关闭
|
||||
- 集群内或集群与用户之间的网络分区
|
||||
- Kubernetes 软件崩溃
|
||||
- 持久存储(例如 GCE PD 或 AWS EBS 卷)的数据丢失或不可用
|
||||
- 操作员错误,例如配置错误的 Kubernetes 软件或应用程序软件
|
||||
|
||||
<!--
|
||||
### Specific scenarios
|
||||
|
||||
- API server VM shutdown or apiserver crashing
|
||||
- Results
|
||||
- unable to stop, update, or start new pods, services, replication controller
|
||||
- existing pods and services should continue to work normally, unless they depend on the Kubernetes API
|
||||
- API server backing storage lost
|
||||
- Results
|
||||
- the kube-apiserver component fails to start successfully and become healthy
|
||||
- kubelets will not be able to reach it but will continue to run the same pods and provide the same service proxying
|
||||
- manual recovery or recreation of apiserver state necessary before apiserver is restarted
|
||||
-->
|
||||
### 具体情况 {#specific-scenarios}
|
||||
|
||||
- API 服务器所在的 VM 关机或者 API 服务器崩溃
|
||||
- 结果
|
||||
- 不能停止、更新或者启动新的 Pod、服务或副本控制器
|
||||
- 现有的 Pod 和服务在不依赖 Kubernetes API 的情况下应该能继续正常工作
|
||||
- API 服务器的后端存储丢失
|
||||
- 结果
|
||||
- kube-apiserver 组件未能成功启动并变健康
|
||||
- kubelet 将不能访问 API 服务器,但是能够继续运行之前的 Pod 和提供相同的服务代理
|
||||
- 在 API 服务器重启之前,需要手动恢复或者重建 API 服务器的状态
|
||||
<!--
|
||||
- Supporting services (node controller, replication controller manager, scheduler, etc) VM shutdown or crashes
|
||||
- currently those are colocated with the apiserver, and their unavailability has similar consequences as apiserver
|
||||
- in future, these will be replicated as well and may not be co-located
|
||||
- they do not have their own persistent state
|
||||
- Individual node (VM or physical machine) shuts down
|
||||
- Results
|
||||
- pods on that Node stop running
|
||||
- Network partition
|
||||
- Results
|
||||
- partition A thinks the nodes in partition B are down; partition B thinks the apiserver is down. (Assuming the master VM ends up in partition A.)
|
||||
-->
|
||||
- Kubernetes 服务组件(节点控制器、副本控制器管理器、调度器等)所在的 VM 关机或者崩溃
|
||||
- 当前,这些控制器是和 API 服务器在一起运行的,它们不可用的现象是与 API 服务器类似的
|
||||
- 将来,这些控制器也会复制为多份,并且可能不在运行于同一节点上
|
||||
- 它们没有自己的持久状态
|
||||
- 单个节点(VM 或者物理机)关机
|
||||
- 结果
|
||||
- 此节点上的所有 Pod 都停止运行
|
||||
- 网络分裂
|
||||
- 结果
|
||||
- 分区 A 认为分区 B 中所有的节点都已宕机;分区 B 认为 API 服务器宕机
|
||||
(假定主控节点所在的 VM 位于分区 A 内)。
|
||||
<!--
|
||||
- Kubelet software fault
|
||||
- Results
|
||||
- crashing kubelet cannot start new pods on the node
|
||||
- kubelet might delete the pods or not
|
||||
- node marked unhealthy
|
||||
- replication controllers start new pods elsewhere
|
||||
- Cluster operator error
|
||||
- Results
|
||||
- loss of pods, services, etc
|
||||
- lost of apiserver backing store
|
||||
- users unable to read API
|
||||
- etc.
|
||||
-->
|
||||
- kubelet 软件故障
|
||||
- 结果
|
||||
- 崩溃的 kubelet 就不能在其所在的节点上启动新的 Pod
|
||||
- kubelet 可能删掉 Pod 或者不删
|
||||
- 节点被标识为非健康态
|
||||
- 副本控制器会在其它的节点上启动新的 Pod
|
||||
- 集群操作错误
|
||||
- 结果
|
||||
- 丢失 Pod 或服务等等
|
||||
- 丢失 API 服务器的后端存储
|
||||
- 用户无法读取API
|
||||
- 等等
|
||||
|
||||
<!--
|
||||
### Mitigations:
|
||||
|
||||
- Action: Use IaaS provider's automatic VM restarting feature for IaaS VMs
|
||||
- Mitigates: Apiserver VM shutdown or apiserver crashing
|
||||
- Mitigates: Supporting services VM shutdown or crashes
|
||||
|
||||
- Action: Use IaaS providers reliable storage (e.g. GCE PD or AWS EBS volume) for VMs with apiserver+etcd
|
||||
- Mitigates: Apiserver backing storage lost
|
||||
|
||||
- Action: Use [high-availability](/docs/setup/production-environment/tools/kubeadm/high-availability/) configuration
|
||||
- Mitigates: Control plane node shutdown or control plane components (scheduler, API server, controller-manager) crashing
|
||||
- Will tolerate one or more simultaneous node or component failures
|
||||
- Mitigates: API server backing storage (i.e., etcd's data directory) lost
|
||||
- Assumes HA (highly-available) etcd configuration
|
||||
-->
|
||||
### 缓解措施 {#mitigations}
|
||||
|
||||
- 措施:对于 IaaS 上的 VM,使用 IaaS 的自动 VM 重启功能
|
||||
- 缓解:API 服务器 VM 关机或 API 服务器崩溃
|
||||
- 缓解:Kubernetes 服务组件所在的 VM 关机或崩溃
|
||||
|
||||
- 措施: 对于运行 API 服务器和 etcd 的 VM,使用 IaaS 提供的可靠的存储(例如 GCE PD 或者 AWS EBS 卷)
|
||||
- 缓解:API 服务器后端存储的丢失
|
||||
|
||||
- 措施:使用[高可用性](/zh/docs/setup/production-environment/tools/kubeadm/high-availability/)的配置
|
||||
- 缓解:主控节点 VM 关机或者主控节点组件(调度器、API 服务器、控制器管理器)崩馈
|
||||
- 将容许一个或多个节点或组件同时出现故障
|
||||
- 缓解:API 服务器后端存储(例如 etcd 的数据目录)丢失
|
||||
- 假定你使用了高可用的 etcd 配置
|
||||
|
||||
<!--
|
||||
- Action: Snapshot apiserver PDs/EBS-volumes periodically
|
||||
- Mitigates: Apiserver backing storage lost
|
||||
- Mitigates: Some cases of operator error
|
||||
- Mitigates: Some cases of Kubernetes software fault
|
||||
|
||||
- Action: use replication controller and services in front of pods
|
||||
- Mitigates: Node shutdown
|
||||
- Mitigates: Kubelet software fault
|
||||
|
||||
- Action: applications (containers) designed to tolerate unexpected restarts
|
||||
- Mitigates: Node shutdown
|
||||
- Mitigates: Kubelet software fault
|
||||
-->
|
||||
- 措施:定期对 API 服务器的 PDs/EBS 卷执行快照操作
|
||||
- 缓解:API 服务器后端存储丢失
|
||||
- 缓解:一些操作错误的场景
|
||||
- 缓解:一些 Kubernetes 软件本身故障的场景
|
||||
|
||||
- 措施:在 Pod 的前面使用副本控制器或服务
|
||||
- 缓解:节点关机
|
||||
- 缓解:kubelet 软件故障
|
||||
|
||||
- 措施:应用(容器)设计成容许异常重启
|
||||
- 缓解:节点关机
|
||||
- 缓解:kubelet 软件故障
|
||||
|
||||
## {{% heading "whatsnext" %}}
|
||||
|
||||
<!--
|
||||
* Learn about the metrics available in the [Resource Metrics Pipeline](resource-metrics-pipeline)
|
||||
* Discover additional tools for [monitoring resource usage](resource-usage-monitoring)
|
||||
* Use Node Problem Detector to [monitor node health](monitor-node-health)
|
||||
* Use `crictl` to [debug Kubernetes nodes](crictl)
|
||||
* Get more information about [Kubernetes auditing](audit)
|
||||
* Use `telepresence` to [develop and debug services locally](local-debugging)
|
||||
-->
|
||||
* 了解[资源指标管道](resource-metrics-pipeline)中可用的指标
|
||||
* 发现用于[监控资源使用](resource-usage-monitoring)的其他工具
|
||||
* 使用节点问题检测器[监控节点健康](monitor-node-health)
|
||||
* 使用 `crictl` 来[调试 Kubernetes 节点](crictl)
|
||||
* 获取更多关于 [Kubernetes 审计](audit)的信息
|
||||
* 使用 `telepresence` [本地开发和调试服务](local-debugging)
|
||||
@@ -0,0 +1,453 @@
|
||||
---
|
||||
title: 审计
|
||||
content_type: concept
|
||||
---
|
||||
<!--
|
||||
reviewers:
|
||||
- soltysh
|
||||
- sttts
|
||||
- ericchiang
|
||||
content_type: concept
|
||||
title: Auditing
|
||||
-->
|
||||
<!-- overview -->
|
||||
|
||||
{{< feature-state state="beta" >}}
|
||||
|
||||
<!--
|
||||
Kubernetes _auditing_ provides a security-relevant, chronological set of records documenting
|
||||
the sequence of actions in a cluster. The cluster audits the activities generated by users,
|
||||
by applications that use the Kubernetes API, and by the control plane itself.
|
||||
|
||||
Auditing allows cluster administrators to answer the following questions:
|
||||
-->
|
||||
Kubernetes _审计(Auditing)_ 功能提供了与安全相关的、按时间顺序排列的记录集,
|
||||
记录每个用户、使用 Kubernetes API 的应用以及控制面自身引发的活动。
|
||||
|
||||
审计功能使得集群管理员能够回答以下问题:
|
||||
|
||||
<!--
|
||||
- what happened?
|
||||
- when did it happen?
|
||||
- who initiated it?
|
||||
- on what did it happen?
|
||||
- where was it observed?
|
||||
- from where was it initiated?
|
||||
- to where was it going?
|
||||
-->
|
||||
- 发生了什么?
|
||||
- 什么时候发生的?
|
||||
- 谁触发的?
|
||||
- 活动发生在哪个(些)对象上?
|
||||
- 在哪观察到的?
|
||||
- 它从哪触发的?
|
||||
- 活动的后续处理行为是什么?
|
||||
|
||||
<!-- body -->
|
||||
|
||||
<!--
|
||||
Audit records begin their lifecycle inside the
|
||||
[kube-apiserver](/docs/reference/command-line-tools-reference/kube-apiserver/)
|
||||
component. Each request on each stage
|
||||
of its execution generates an audit event, which is then pre-processed according to
|
||||
a certain policy and written to a backend. The policy determines what's recorded
|
||||
and the backends persist the records. The current backend implementations
|
||||
include logs files and webhooks.
|
||||
-->
|
||||
审计记录最初产生于
|
||||
[kube-apiserver](/zh/docs/reference/command-line-tools-reference/kube-apiserver/)
|
||||
内部。每个请求在不同执行阶段都会生成审计事件;这些审计事件会根据特定策略
|
||||
被预处理并写入后端。策略确定要记录的内容和用来存储记录的后端。
|
||||
当前的后端支持日志文件和 webhook。
|
||||
|
||||
<!--
|
||||
Each request can be recorded with an associated _stage_. The defined stages are:
|
||||
|
||||
- `RequestReceived` - The stage for events generated as soon as the audit
|
||||
handler receives the request, and before it is delegated down the handler
|
||||
chain.
|
||||
- `ResponseStarted` - Once the response headers are sent, but before the
|
||||
response body is sent. This stage is only generated for long-running requests
|
||||
(e.g. watch).
|
||||
- `ResponseComplete` - The response body has been completed and no more bytes
|
||||
will be sent.
|
||||
- `Panic` - Events generated when a panic occurred.
|
||||
-->
|
||||
每个请求都可被记录其相关的 _阶段(stage)_。已定义的阶段有:
|
||||
|
||||
- `RequestReceived` - 此阶段对应审计处理器接收到请求后,并且在委托给
|
||||
其余处理器之前生成的事件。
|
||||
- `ResponseStarted` - 在响应消息的头部发送后,响应消息体发送前生成的事件。
|
||||
只有长时间运行的请求(例如 watch)才会生成这个阶段。
|
||||
- `ResponseComplete` - 当响应消息体完成并且没有更多数据需要传输的时候。
|
||||
- `Panic` - 当 panic 发生时生成。
|
||||
|
||||
<!--
|
||||
The configuration of an
|
||||
[Audit Event configuration](/docs/reference/config-api/apiserver-audit.v1/#audit-k8s-io-v1-Event)
|
||||
is different from the
|
||||
[Event](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#event-v1-core)
|
||||
API object.
|
||||
-->
|
||||
{{< note >}}
|
||||
[审计事件配置](/zh/docs/reference/config-api/apiserver-audit.v1/#audit-k8s-io-v1-Event)
|
||||
的配置与 [Event](/zh/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#event-v1-core)
|
||||
API 对象不同。
|
||||
{{< /note >}}
|
||||
|
||||
<!--
|
||||
The audit logging feature increases the memory consumption of the API server
|
||||
because some context required for auditing is stored for each request.
|
||||
Additionally, memory consumption depends on the audit logging configuration.
|
||||
-->
|
||||
审计日志记录功能会增加 API server 的内存消耗,因为需要为每个请求存储审计所需的某些上下文。
|
||||
此外,内存消耗取决于审计日志记录的配置。
|
||||
|
||||
<!--
|
||||
## Audit Policy
|
||||
|
||||
Audit policy defines rules about what events should be recorded and what data
|
||||
they should include. The audit policy object structure is defined in the
|
||||
[`audit.k8s.io` API group](/docs/reference/config-api/apiserver-audit.v1/#audit-k8s-io-v1-Policy).
|
||||
When an event is processed, it's
|
||||
compared against the list of rules in order. The first matching rule sets the
|
||||
_audit level_ of the event. The defined audit levels are:
|
||||
-->
|
||||
## 审计策略 {#audit-policy}
|
||||
|
||||
审计政策定义了关于应记录哪些事件以及应包含哪些数据的规则。
|
||||
审计策略对象结构定义在
|
||||
[`audit.k8s.io` API 组](/zh/docs/reference/config-api/apiserver-audit.v1/#audit-k8s-io-v1-Policy)
|
||||
处理事件时,将按顺序与规则列表进行比较。第一个匹配规则设置事件的
|
||||
_审计级别(Audit Level)_。已定义的审计级别有:
|
||||
|
||||
<!--
|
||||
- `None` - don't log events that match this rule.
|
||||
- `Metadata` - log request metadata (requesting user, timestamp, resource,
|
||||
verb, etc.) but not request or response body.
|
||||
- `Request` - log event metadata and request body but not response body.
|
||||
This does not apply for non-resource requests.
|
||||
- `RequestResponse` - log event metadata, request and response bodies.
|
||||
This does not apply for non-resource requests.
|
||||
-->
|
||||
- `None` - 符合这条规则的日志将不会记录。
|
||||
- `Metadata` - 记录请求的元数据(请求的用户、时间戳、资源、动词等等),
|
||||
但是不记录请求或者响应的消息体。
|
||||
- `Request` - 记录事件的元数据和请求的消息体,但是不记录响应的消息体。
|
||||
这不适用于非资源类型的请求。
|
||||
- `RequestResponse` - 记录事件的元数据,请求和响应的消息体。这不适用于非资源类型的请求。
|
||||
|
||||
<!--
|
||||
You can pass a file with the policy to `kube-apiserver`
|
||||
using the `--audit-policy-file` flag. If the flag is omitted, no events are logged.
|
||||
Note that the `rules` field __must__ be provided in the audit policy file.
|
||||
A policy with no (0) rules is treated as illegal.
|
||||
|
||||
Below is an example audit policy file:
|
||||
-->
|
||||
你可以使用 `--audit-policy-file` 标志将包含策略的文件传递给 `kube-apiserver`。
|
||||
如果不设置该标志,则不记录事件。
|
||||
注意 `rules` 字段 __必须__ 在审计策略文件中提供。没有(0)规则的策略将被视为非法配置。
|
||||
|
||||
以下是一个审计策略文件的示例:
|
||||
|
||||
{{< codenew file="audit/audit-policy.yaml" >}}
|
||||
|
||||
<!--
|
||||
You can use a minimal audit policy file to log all requests at the `Metadata` level:
|
||||
-->
|
||||
你可以使用最低限度的审计策略文件在 `Metadata` 级别记录所有请求:
|
||||
|
||||
```yaml
|
||||
# 在 Metadata 级别为所有请求生成日志
|
||||
apiVersion: audit.k8s.io/v1beta1
|
||||
kind: Policy
|
||||
rules:
|
||||
- level: Metadata
|
||||
```
|
||||
|
||||
<!--
|
||||
If you're crafting your own audit profile, you can use the audit profile for Google Container-Optimized OS as a starting point. You can check the
|
||||
[configure-helper.sh](https://github.com/kubernetes/kubernetes/blob/master/cluster/gce/gci/configure-helper.sh)
|
||||
script, which generates the audit policy file. You can see most of the audit policy file by looking directly at the script.
|
||||
|
||||
You can also refer to the [`Policy` configuration reference](/docs/reference/config-api/apiserver-audit.v1/#audit-k8s-io-v1-Policy)
|
||||
for details about the fields defined.
|
||||
-->
|
||||
如果你在打磨自己的审计配置文件,你可以使用为 Google Container-Optimized OS
|
||||
设计的审计配置作为出发点。你可以参考
|
||||
[configure-helper.sh](https://github.com/kubernetes/kubernetes/blob/master/cluster/gce/gci/configure-helper.sh)
|
||||
脚本,该脚本能够生成审计策略文件。你可以直接在脚本中看到审计策略的绝大部份内容。
|
||||
|
||||
你也可以参考 [`Policy` 配置参考](/zh/docs/reference/config-api/apiserver-audit.v1/#audit-k8s-io-v1-Policy)
|
||||
以获取有关已定义字段的详细信息。
|
||||
|
||||
<!--
|
||||
## Audit backends
|
||||
|
||||
Audit backends persist audit events to an external storage.
|
||||
Out of the box, the kube-apiserver provides two backends:
|
||||
|
||||
- Log backend, which writes events into the filesystem
|
||||
- Webhook backend, which sends events to an external HTTP API
|
||||
|
||||
In all cases, audit events follow a structure defined by the Kubernetes API in the
|
||||
[`audit.k8s.io` API group](/docs/reference/config-api/apiserver-audit.v1/#audit-k8s-io-v1-Event).
|
||||
-->
|
||||
|
||||
## 审计后端 {#audit-backends}
|
||||
|
||||
审计后端实现将审计事件导出到外部存储。`Kube-apiserver` 默认提供两个后端:
|
||||
|
||||
- Log 后端,将事件写入到文件系统
|
||||
- Webhook 后端,将事件发送到外部 HTTP API
|
||||
|
||||
在这所有情况下,审计事件均遵循 Kubernetes API 在
|
||||
[`audit.k8s.io` API 组](/zh/docs/reference/config-api/apiserver-audit.v1/#audit-k8s-io-v1-Event)
|
||||
中定义的结构。
|
||||
|
||||
<!--
|
||||
In case of patches, request body is a JSON array with patch operations, not a JSON object
|
||||
with an appropriate Kubernetes API object. For example, the following request body is a valid patch
|
||||
request to `/apis/batch/v1/namespaces/some-namespace/jobs/some-job-name`.
|
||||
-->
|
||||
{{< note >}}
|
||||
对于 patch 请求,请求的消息体需要是设定 patch 操作的 JSON 所构成的一个串,
|
||||
而不是一个完整的 Kubernetes API 对象 JSON 串。
|
||||
例如,以下的示例是一个合法的 patch 请求消息体,该请求对应
|
||||
`/apis/batch/v1/namespaces/some-namespace/jobs/some-job-name`。
|
||||
|
||||
```json
|
||||
[
|
||||
{
|
||||
"op": "replace",
|
||||
"path": "/spec/parallelism",
|
||||
"value": 0
|
||||
},
|
||||
{
|
||||
"op": "remove",
|
||||
"path": "/spec/template/spec/containers/0/terminationMessagePolicy"
|
||||
}
|
||||
]
|
||||
```
|
||||
{{< /note >}}
|
||||
|
||||
<!--
|
||||
### Log backend
|
||||
|
||||
The log backend writes audit events to a file in [JSONlines](https://jsonlines.org/) format.
|
||||
You can configure the log audit backend using the following `kube-apiserver` flags:
|
||||
|
||||
Log backend writes audit events to a file in JSON format. You can configure
|
||||
log audit backend using the following [kube-apiserver][kube-apiserver] flags:
|
||||
-->
|
||||
### Log 后端
|
||||
|
||||
Log 后端将审计事件写入 [JSONlines](https://jsonlines.org/) 格式的文件。
|
||||
你可以使用以下 `kube-apiserver` 标志配置 Log 审计后端:
|
||||
|
||||
<!--
|
||||
- `--audit-log-path` specifies the log file path that log backend uses to write
|
||||
audit events. Not specifying this flag disables log backend. `-` means standard out
|
||||
- `--audit-log-maxage` defined the maximum number of days to retain old audit log files
|
||||
- `--audit-log-maxbackup` defines the maximum number of audit log files to retain
|
||||
- `--audit-log-maxsize` defines the maximum size in megabytes of the audit log file before it gets rotated
|
||||
-->
|
||||
- `--audit-log-path` 指定用来写入审计事件的日志文件路径。不指定此标志会禁用日志后端。`-` 意味着标准化
|
||||
- `--audit-log-maxage` 定义保留旧审计日志文件的最大天数
|
||||
- `--audit-log-maxbackup` 定义要保留的审计日志文件的最大数量
|
||||
- `--audit-log-maxsize` 定义审计日志文件的最大大小(兆字节)
|
||||
|
||||
<!--
|
||||
If your cluster's control plane runs the kube-apiserver as a Pod, remember to mount the `hostPath`
|
||||
to the location of the policy file and log file, so that audit records are persisted. For example:
|
||||
-->
|
||||
如果你的集群控制面以 Pod 的形式运行 kube-apiserver,记得要通过 `hostPath`
|
||||
卷来访问策略文件和日志文件所在的目录,这样审计记录才会持久保存下来。例如:
|
||||
|
||||
```shell
|
||||
--audit-policy-file=/etc/kubernetes/audit-policy.yaml
|
||||
--audit-log-path=/var/log/kubernetes/audit/audit.log
|
||||
```
|
||||
|
||||
接下来挂载数据卷:
|
||||
|
||||
```yaml
|
||||
volumeMounts:
|
||||
- mountPath: /etc/kubernetes/audit-policy.yaml
|
||||
name: audit
|
||||
readOnly: true
|
||||
- mountPath: /var/log/kubernetes/audit/
|
||||
name: audit-log
|
||||
readOnly: false
|
||||
```
|
||||
|
||||
<!--
|
||||
and finally configure the `hostPath`:
|
||||
-->
|
||||
最后配置 `hostPath`:
|
||||
|
||||
```yaml
|
||||
...
|
||||
volumes:
|
||||
- name: audit
|
||||
hostPath:
|
||||
path: /etc/kubernetes/audit-policy.yaml
|
||||
type: File
|
||||
|
||||
- name: audit-log
|
||||
hostPath:
|
||||
path: /var/log/kubernetes/audit/
|
||||
type: DirectoryOrCreate
|
||||
```
|
||||
|
||||
<!--
|
||||
### Webhook backend
|
||||
|
||||
The webhook audit backend sends audit events to a remote web API, which is assumed to
|
||||
be a form of the Kubernetes API, including means of authentication. You can configure
|
||||
a webhook audit backend using the following kube-apiserver flags:
|
||||
-->
|
||||
### Webhook 后端 {#webhook-backend}
|
||||
|
||||
Webhook 后端将审计事件发送到远程 Web API,该远程 API 应该暴露与 `kube-apiserver`
|
||||
形式相同的 API,包括其身份认证机制。你可以使用如下 kube-apiserver 标志来配置
|
||||
Webhook 审计后端:
|
||||
|
||||
<!--
|
||||
- `--audit-webhook-config-file` specifies the path to a file with a webhook
|
||||
configuration. The webhook configuration is effectively a specialized
|
||||
[kubeconfig](/docs/tasks/access-application-cluster/configure-access-multiple-clusters).
|
||||
- `--audit-webhook-initial-backoff` specifies the amount of time to wait after the first failed
|
||||
request before retrying. Subsequent requests are retried with exponential backoff.
|
||||
|
||||
The webhook config file uses the kubeconfig format to specify the remote address of
|
||||
the service and credentials used to connect to it.
|
||||
-->
|
||||
- `--audit-webhook-config-file` 设置 Webhook 配置文件的路径。Webhook 配置文件实际上是一个
|
||||
[kubeconfig 文件](/zh/docs/concepts/configuration/organize-cluster-access-kubeconfig/)。
|
||||
- `--audit-webhook-initial-backoff` 指定在第一次失败后重发请求等待的时间。随后的请求将以指数退避重试。
|
||||
|
||||
Webhook 配置文件使用 kubeconfig 格式指定服务的远程地址和用于连接它的凭据。
|
||||
|
||||
<!--
|
||||
## Event batching {#batching}
|
||||
|
||||
Both log and webhook backends support batching. Using webhook as an example, here's the list of
|
||||
available flags. To get the same flag for log backend, replace `webhook` with `log` in the flag
|
||||
name. By default, batching is enabled in `webhook` and disabled in `log`. Similarly, by default
|
||||
throttling is enabled in `webhook` and disabled in `log`.
|
||||
-->
|
||||
## 事件批处理 {#batching}
|
||||
|
||||
日志和 Webhook 后端都支持批处理。以 Webhook 为例,以下是可用参数列表。要获取日志
|
||||
后端的同样参数,请在参数名称中将 `webhook` 替换为 `log`。
|
||||
默认情况下,在 `webhook` 中批处理是被启用的,在 `log` 中批处理是被禁用的。
|
||||
同样,默认情况下,在 `webhook` 中启用带宽限制,在 `log` 中禁用带宽限制。
|
||||
|
||||
<!--
|
||||
- `--audit-webhook-mode` defines the buffering strategy. One of the following:
|
||||
- `batch` - buffer events and asynchronously process them in batches. This is the default.
|
||||
- `blocking` - block API server responses on processing each individual event.
|
||||
- `blocking-strict` - Same as blocking, but when there is a failure during audit logging at the
|
||||
RequestReceived stage, the whole request to the kube-apiserver fails.
|
||||
-->
|
||||
- `--audit-webhook-mode` 定义缓存策略,可选值如下:
|
||||
- `batch` - 以批处理缓存事件和异步的过程。这是默认值。
|
||||
- `blocking` - 在 API 服务器处理每个单独事件时,阻塞其响应。
|
||||
- `blocking-strict` - 与 `blocking` 相同,不过当审计日志在 RequestReceived 阶段
|
||||
失败时,整个 API 服务请求会失效。
|
||||
|
||||
<!--
|
||||
The following flags are used only in the `batch` mode.
|
||||
|
||||
- `--audit-webhook-batch-buffer-size` defines the number of events to buffer before batching.
|
||||
If the rate of incoming events overflows the buffer, events are dropped.
|
||||
- `--audit-webhook-batch-max-size` defines the maximum number of events in one batch.
|
||||
- `--audit-webhook-batch-max-wait` defines the maximum amount of time to wait before unconditionally
|
||||
batching events in the queue.
|
||||
- `--audit-webhook-batch-throttle-qps` defines the maximum average number of batches generated
|
||||
per second.
|
||||
- `--audit-webhook-batch-throttle-burst` defines the maximum number of batches generated at the same
|
||||
moment if the allowed QPS was underutilized previously.
|
||||
-->
|
||||
以下参数仅用于 `batch` 模式。
|
||||
|
||||
- `--audit-webhook-batch-buffer-size` 定义 batch 之前要缓存的事件数。
|
||||
如果传入事件的速率溢出缓存区,则会丢弃事件。
|
||||
- `--audit-webhook-batch-max-size` 定义一个 batch 中的最大事件数。
|
||||
- `--audit-webhook-batch-max-wait` 无条件 batch 队列中的事件前等待的最大事件。
|
||||
- `--audit-webhook-batch-throttle-qps` 每秒生成的最大批次数。
|
||||
- `--audit-webhook-batch-throttle-burst` 在达到允许的 QPS 前,同一时刻允许存在的最大 batch 生成数。
|
||||
|
||||
<!--
|
||||
## Parameter tuning
|
||||
|
||||
Parameters should be set to accommodate the load on the API server.
|
||||
|
||||
For example, if kube-apiserver receives 100 requests each second, and each request is audited only
|
||||
on `ResponseStarted` and `ResponseComplete` stages, you should account for ≅200 audit
|
||||
events being generated each second. Assuming that there are up to 100 events in a batch,
|
||||
you should set throttling level at least 2 queries per second. Assuming that the backend can take up to
|
||||
5 seconds to write events, you should set the buffer size to hold up to 5 seconds of events;
|
||||
that is: 10 batches, or 1000 events.
|
||||
-->
|
||||
## 参数调整 {#parameter-tuning}
|
||||
|
||||
需要设置参数以适应 API 服务器上的负载。
|
||||
|
||||
例如,如果 kube-apiserver 每秒收到 100 个请求,并且每个请求仅在 `ResponseStarted`
|
||||
和 `ResponseComplete` 阶段进行审计,则应该考虑每秒生成约 200 个审计事件。
|
||||
假设批处理中最多有 100 个事件,则应将限制级别设置为每秒至少 2 个查询。
|
||||
假设后端最多需要 5 秒钟来写入事件,你应该设置缓冲区大小以容纳最多 5 秒的事件,
|
||||
即 10 个 batch,即 1000 个事件。
|
||||
|
||||
<!--
|
||||
In most cases however, the default parameters should be sufficient and you don't have to worry about
|
||||
setting them manually. You can look at the following Prometheus metrics exposed by kube-apiserver
|
||||
and in the logs to monitor the state of the auditing subsystem.
|
||||
|
||||
- `apiserver_audit_event_total` metric contains the total number of audit events exported.
|
||||
- `apiserver_audit_error_total` metric contains the total number of events dropped due to an error
|
||||
during exporting.
|
||||
-->
|
||||
但是,在大多数情况下,默认参数应该足够了,你不必手动设置它们。
|
||||
你可以查看 kube-apiserver 公开的以下 Prometheus 指标,并在日志中监控审计子系统的状态。
|
||||
|
||||
- `apiserver_audit_event_total` 包含所有暴露的审计事件数量的指标。
|
||||
- `apiserver_audit_error_total` 在暴露时由于发生错误而被丢弃的事件的数量。
|
||||
|
||||
<!--
|
||||
### Log entry truncation {#truncate}
|
||||
|
||||
Both log and webhook backends support limiting the size of events that are logged.
|
||||
As an example, the following is the list of flags available for the log backend:
|
||||
-->
|
||||
### 日志条目截断 {#truncate}
|
||||
|
||||
日志后端和 Webhook 后端都支持限制所输出的事件的尺寸。
|
||||
例如,下面是可以为日志后端配置的标志列表:
|
||||
|
||||
<!--
|
||||
- `audit-log-truncate-enabled` whether event and batch truncating is enabled.
|
||||
- `audit-log-truncate-max-batch-size` maximum size in bytes of the batch sent to the underlying backend.
|
||||
- `audit-log-truncate-max-event-size` maximum size in bytes of the audit event sent to the underlying backend.
|
||||
-->
|
||||
- `audit-log-truncate-enabled`:是否弃用事件和批次的截断处理。
|
||||
- `audit-log-truncate-max-batch-size`:向下层后端发送的各批次的最大尺寸字节数。
|
||||
- `audit-log-truncate-max-event-size`:向下层后端发送的审计事件的最大尺寸字节数。
|
||||
|
||||
<!--
|
||||
By default truncate is disabled in both `webhook` and `log`, a cluster administrator should set
|
||||
`audit-log-truncate-enabled` or `audit-webhook-truncate-enabled` to enable the feature.
|
||||
-->
|
||||
默认情况下,截断操作在 `webhook` 和 `log` 后端都是被禁用的,集群管理员需要设置
|
||||
`audit-log-truncate-enabled` 或 `audit-webhook-truncate-enabled` 标志来启用此操作。
|
||||
|
||||
## {{% heading "whatsnext" %}}
|
||||
|
||||
<!--
|
||||
* Learn about [Mutating webhook auditing annotations](/docs/reference/access-authn-authz/extensible-admission-controllers/#mutating-webhook-auditing-annotations).
|
||||
-->
|
||||
* 了解 [Mutating webhook 审计注解](/zh/docs/reference/access-authn-authz/extensible-admission-controllers/#mutating-webhook-auditing-annotations)。
|
||||
|
||||
@@ -0,0 +1,563 @@
|
||||
---
|
||||
title: 使用 crictl 对 Kubernetes 节点进行调试
|
||||
content_type: task
|
||||
weight: 30
|
||||
---
|
||||
<!--
|
||||
reviewers:
|
||||
- Random-Liu
|
||||
- feiskyer
|
||||
- mrunalp
|
||||
title: Debugging Kubernetes nodes with crictl
|
||||
content_type: task
|
||||
weight: 30
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
{{< feature-state for_k8s_version="v1.11" state="stable" >}}
|
||||
|
||||
<!--
|
||||
`crictl` is a command-line interface for CRI-compatible container runtimes.
|
||||
You can use it to inspect and debug container runtimes and applications on a
|
||||
Kubernetes node. `crictl` and its source are hosted in the
|
||||
[cri-tools](https://github.com/kubernetes-sigs/cri-tools) repository.
|
||||
-->
|
||||
|
||||
`crictl` 是 CRI 兼容的容器运行时命令行接口。
|
||||
你可以使用它来检查和调试 Kubernetes 节点上的容器运行时和应用程序。
|
||||
`crictl` 和它的源代码在
|
||||
[cri-tools](https://github.com/kubernetes-sigs/cri-tools) 代码库。
|
||||
|
||||
## {{% heading "prerequisites" %}}
|
||||
|
||||
<!--
|
||||
`crictl` requires a Linux operating system with a CRI runtime.
|
||||
-->
|
||||
`crictl` 需要带有 CRI 运行时的 Linux 操作系统。
|
||||
|
||||
<!-- steps -->
|
||||
|
||||
<!--
|
||||
## Installing crictl
|
||||
|
||||
You can download a compressed archive `crictl` from the cri-tools
|
||||
[release page](https://github.com/kubernetes-sigs/cri-tools/releases), for several
|
||||
different architectures. Download the version that corresponds to your version
|
||||
of Kubernetes. Extract it and move it to a location on your system path, such as
|
||||
`/usr/local/bin/`.
|
||||
-->
|
||||
## 安装 crictl {#installing-crictl}
|
||||
|
||||
你可以从 cri-tools [发布页面](https://github.com/kubernetes-sigs/cri-tools/releases)
|
||||
下载一个压缩的 `crictl` 归档文件,用于几种不同的架构。
|
||||
下载与你的 kubernetes 版本相对应的版本。
|
||||
提取它并将其移动到系统路径上的某个位置,例如`/usr/local/bin/`。
|
||||
|
||||
<!--
|
||||
## General usage
|
||||
|
||||
The `crictl` command has several subcommands and runtime flags. Use
|
||||
`crictl help` or `crictl <subcommand> help` for more details.
|
||||
-->
|
||||
## 一般用法 {#general-usage}
|
||||
|
||||
`crictl` 命令有几个子命令和运行时参数。
|
||||
有关详细信息,请使用 `crictl help` 或 `crictl <subcommand> help` 获取帮助信息。
|
||||
|
||||
<!--
|
||||
You can set the endpoint for `crictl` by doing one of the following:
|
||||
-->
|
||||
你可以用以下方法之一来为 `crictl` 设置端点:
|
||||
|
||||
<!--
|
||||
* Set the `--runtime-endpoint` and `--image-endpoint` flags.
|
||||
* Set the `CONTAINER_RUNTIME_ENDPOINT` and `IMAGE_SERVICE_ENDPOINT` environment
|
||||
variables.
|
||||
* Set the endpoint in the configuration file `/etc/crictl.yaml`. To specify a
|
||||
different file, use the `--config=PATH_TO_FILE` flag when you run `crictl`.
|
||||
-->
|
||||
- 设置参数 `--runtime-endpoint` 和 `--image-endpoint`。
|
||||
- 设置环境变量 `CONTAINER_RUNTIME_ENDPOINT` 和 `IMAGE_SERVICE_ENDPOINT`。
|
||||
- 在配置文件 `--config=/etc/crictl.yaml` 中设置端点。
|
||||
要设置不同的文件,可以在运行 `crictl` 时使用 `--config=PATH_TO_FILE` 标志。
|
||||
|
||||
<!--
|
||||
You can also specify timeout values when connecting to the server and enable or
|
||||
disable debugging, by specifying `timeout` or `debug` values in the configuration
|
||||
file or using the `--timeout` and `--debug` command-line flags.
|
||||
-->
|
||||
你还可以在连接到服务器并启用或禁用调试时指定超时值,方法是在配置文件中指定
|
||||
`timeout` 或 `debug` 值,或者使用 `--timeout` 和 `--debug` 命令行参数。
|
||||
|
||||
<!--
|
||||
To view or edit the current configuration, view or edit the contents of
|
||||
`/etc/crictl.yaml`. For example, the configuration when using the `containerd`
|
||||
container runtime would be similar to this:
|
||||
-->
|
||||
要查看或编辑当前配置,请查看或编辑 `/etc/crictl.yaml` 的内容。
|
||||
例如,使用 `containerd` 容器运行时的配置会类似于这样:
|
||||
|
||||
```
|
||||
runtime-endpoint: unix:///var/run/containerd/containerd.sock
|
||||
image-endpoint: unix:///var/run/containerd/containerd.sock
|
||||
timeout: 10
|
||||
debug: true
|
||||
```
|
||||
|
||||
<!--
|
||||
To learn more about `crictl`, refer to the [`crictl`
|
||||
documentation](https://github.com/kubernetes-sigs/cri-tools/blob/master/docs/crictl.md).
|
||||
-->
|
||||
要进一步了解 `crictl`,参阅
|
||||
[`crictl` 文档](https://github.com/kubernetes-sigs/cri-tools/blob/master/docs/crictl.md)。
|
||||
|
||||
<!--
|
||||
## Example crictl commands
|
||||
|
||||
The following examples show some `crictl` commands and example output.
|
||||
-->
|
||||
## crictl 命令示例 {#example-crictl-commands}
|
||||
|
||||
{{< warning >}}
|
||||
<!--
|
||||
If you use `crictl` to create pod sandboxes or containers on a running
|
||||
Kubernetes cluster, the Kubelet will eventually delete them. `crictl` is not a
|
||||
general purpose workflow tool, but a tool that is useful for debugging.
|
||||
-->
|
||||
如果使用 `crictl` 在正在运行的 Kubernetes 集群上创建 Pod 沙盒或容器,
|
||||
kubelet 最终将删除它们。
|
||||
`crictl` 不是一个通用的工作流工具,而是一个对调试有用的工具。
|
||||
{{< /warning >}}
|
||||
|
||||
<!--
|
||||
### List pods
|
||||
|
||||
List all pods:
|
||||
-->
|
||||
### 打印 Pod 清单 {#list-pods}
|
||||
|
||||
打印所有 Pod 的清单:
|
||||
|
||||
```shell
|
||||
crictl pods
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于:
|
||||
|
||||
```
|
||||
POD ID CREATED STATE NAME NAMESPACE ATTEMPT
|
||||
926f1b5a1d33a About a minute ago Ready sh-84d7dcf559-4r2gq default 0
|
||||
4dccb216c4adb About a minute ago Ready nginx-65899c769f-wv2gp default 0
|
||||
a86316e96fa89 17 hours ago Ready kube-proxy-gblk4 kube-system 0
|
||||
919630b8f81f1 17 hours ago Ready nvidia-device-plugin-zgbbv kube-system 0
|
||||
```
|
||||
|
||||
<!--
|
||||
List pods by name:
|
||||
-->
|
||||
根据名称打印 Pod 清单:
|
||||
|
||||
```shell
|
||||
crictl pods --name nginx-65899c769f-wv2gp
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```
|
||||
POD ID CREATED STATE NAME NAMESPACE ATTEMPT
|
||||
4dccb216c4adb 2 minutes ago Ready nginx-65899c769f-wv2gp default 0
|
||||
```
|
||||
|
||||
<!--
|
||||
List pods by label:
|
||||
-->
|
||||
根据标签打印 Pod 清单:
|
||||
|
||||
```shell
|
||||
crictl pods --label run=nginx
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
POD ID CREATED STATE NAME NAMESPACE ATTEMPT
|
||||
4dccb216c4adb 2 minutes ago Ready nginx-65899c769f-wv2gp default 0
|
||||
```
|
||||
|
||||
<!--
|
||||
### List images
|
||||
|
||||
List all images:
|
||||
-->
|
||||
### 打印镜像清单 {#list-containers}
|
||||
|
||||
打印所有镜像清单:
|
||||
|
||||
```shell
|
||||
crictl images
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
IMAGE TAG IMAGE ID SIZE
|
||||
busybox latest 8c811b4aec35f 1.15MB
|
||||
k8s-gcrio.azureedge.net/hyperkube-amd64 v1.10.3 e179bbfe5d238 665MB
|
||||
k8s-gcrio.azureedge.net/pause-amd64 3.1 da86e6ba6ca19 742kB
|
||||
nginx latest cd5239a0906a6 109MB
|
||||
```
|
||||
|
||||
<!--
|
||||
List images by repository:
|
||||
-->
|
||||
根据仓库打印镜像清单:
|
||||
|
||||
```shell
|
||||
crictl images nginx
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
IMAGE TAG IMAGE ID SIZE
|
||||
nginx latest cd5239a0906a6 109MB
|
||||
```
|
||||
|
||||
<!--
|
||||
Only list image IDs:
|
||||
-->
|
||||
只打印镜像 ID:
|
||||
|
||||
```shell
|
||||
crictl images -q
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
sha256:8c811b4aec35f259572d0f79207bc0678df4c736eeec50bc9fec37ed936a472a
|
||||
sha256:e179bbfe5d238de6069f3b03fccbecc3fb4f2019af741bfff1233c4d7b2970c5
|
||||
sha256:da86e6ba6ca197bf6bc5e9d900febd906b133eaa4750e6bed647b0fbe50ed43e
|
||||
sha256:cd5239a0906a6ccf0562354852fae04bc5b52d72a2aff9a871ddb6bd57553569
|
||||
```
|
||||
|
||||
<!--
|
||||
### List containers
|
||||
|
||||
List all containers:
|
||||
-->
|
||||
### 打印容器清单 {#list-containers}
|
||||
|
||||
打印所有容器清单:
|
||||
|
||||
```shell
|
||||
crictl ps -a
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
CONTAINER ID IMAGE CREATED STATE NAME ATTEMPT
|
||||
1f73f2d81bf98 busybox@sha256:141c253bc4c3fd0a201d32dc1f493bcf3fff003b6df416dea4f41046e0f37d47 7 minutes ago Running sh 1
|
||||
9c5951df22c78 busybox@sha256:141c253bc4c3fd0a201d32dc1f493bcf3fff003b6df416dea4f41046e0f37d47 8 minutes ago Exited sh 0
|
||||
87d3992f84f74 nginx@sha256:d0a8828cccb73397acb0073bf34f4d7d8aa315263f1e7806bf8c55d8ac139d5f 8 minutes ago Running nginx 0
|
||||
1941fb4da154f k8s-gcrio.azureedge.net/hyperkube-amd64@sha256:00d814b1f7763f4ab5be80c58e98140dfc69df107f253d7fdd714b30a714260a 18 hours ago Running kube-proxy 0
|
||||
```
|
||||
|
||||
<!--
|
||||
List running containers:
|
||||
-->
|
||||
打印正在运行的容器清单:
|
||||
|
||||
```shell
|
||||
crictl ps
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
CONTAINER ID IMAGE CREATED STATE NAME ATTEMPT
|
||||
1f73f2d81bf98 busybox@sha256:141c253bc4c3fd0a201d32dc1f493bcf3fff003b6df416dea4f41046e0f37d47 6 minutes ago Running sh 1
|
||||
87d3992f84f74 nginx@sha256:d0a8828cccb73397acb0073bf34f4d7d8aa315263f1e7806bf8c55d8ac139d5f 7 minutes ago Running nginx 0
|
||||
1941fb4da154f k8s-gcrio.azureedge.net/hyperkube-amd64@sha256:00d814b1f7763f4ab5be80c58e98140dfc69df107f253d7fdd714b30a714260a 17 hours ago Running kube-proxy 0
|
||||
```
|
||||
|
||||
<!--
|
||||
### Execute a command in a running container
|
||||
-->
|
||||
### 在正在运行的容器上执行命令 {#execute-a-command-in-a-running-container}
|
||||
|
||||
```shell
|
||||
crictl exec -i -t 1f73f2d81bf98 ls
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
bin dev etc home proc root sys tmp usr var
|
||||
```
|
||||
|
||||
<!--
|
||||
### Get a container's logs
|
||||
|
||||
Get all container logs:
|
||||
-->
|
||||
### 获取容器日志 {#get-a-container-s-logs}
|
||||
|
||||
获取容器的所有日志:
|
||||
|
||||
```shell
|
||||
crictl logs 87d3992f84f74
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
10.240.0.96 - - [06/Jun/2018:02:45:49 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.47.0" "-"
|
||||
10.240.0.96 - - [06/Jun/2018:02:45:50 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.47.0" "-"
|
||||
10.240.0.96 - - [06/Jun/2018:02:45:51 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.47.0" "-"
|
||||
```
|
||||
|
||||
<!--
|
||||
Get only the latest `N` lines of logs:
|
||||
-->
|
||||
获取最近的 `N` 行日志:
|
||||
|
||||
```shell
|
||||
crictl logs --tail=1 87d3992f84f74
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
10.240.0.96 - - [06/Jun/2018:02:45:51 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.47.0" "-"
|
||||
```
|
||||
|
||||
<!--
|
||||
### Run a pod sandbox
|
||||
|
||||
Using `crictl` to run a pod sandbox is useful for debugging container runtimes.
|
||||
On a running Kubernetes cluster, the sandbox will eventually be stopped and
|
||||
deleted by the Kubelet.
|
||||
-->
|
||||
### 运行 Pod 沙盒 {#run-a-pod-sandbox}
|
||||
|
||||
用 `crictl` 运行 Pod 沙盒对容器运行时排错很有帮助。
|
||||
在运行的 Kubernetes 集群中,沙盒会随机地被 kubelet 停止和删除。
|
||||
|
||||
<!--
|
||||
1. Create a JSON file like the following:
|
||||
-->
|
||||
1. 编写下面的 JSON 文件:
|
||||
|
||||
```json
|
||||
{
|
||||
"metadata": {
|
||||
"name": "nginx-sandbox",
|
||||
"namespace": "default",
|
||||
"attempt": 1,
|
||||
"uid": "hdishd83djaidwnduwk28bcsb"
|
||||
},
|
||||
"logDirectory": "/tmp",
|
||||
"linux": {
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
<!--
|
||||
2. Use the `crictl runp` command to apply the JSON and run the sandbox.
|
||||
-->
|
||||
2. 使用 `crictl runp` 命令应用 JSON 文件并运行沙盒。
|
||||
|
||||
```shell
|
||||
crictl runp pod-config.json
|
||||
```
|
||||
|
||||
<!--
|
||||
The ID of the sandbox is returned.
|
||||
-->
|
||||
返回了沙盒的 ID。
|
||||
|
||||
<!--
|
||||
### Create a container
|
||||
|
||||
Using `crictl` to create a container is useful for debugging container runtimes.
|
||||
On a running Kubernetes cluster, the sandbox will eventually be stopped and
|
||||
deleted by the Kubelet.
|
||||
-->
|
||||
### 创建容器 {#create-a-container}
|
||||
|
||||
用 `crictl` 创建容器对容器运行时排错很有帮助。
|
||||
在运行的 Kubernetes 集群中,沙盒会随机的被 kubelet 停止和删除。
|
||||
|
||||
<!--
|
||||
1. Pull a busybox image
|
||||
-->
|
||||
1. 拉取 busybox 镜像
|
||||
|
||||
```shell
|
||||
crictl pull busybox
|
||||
```
|
||||
```none
|
||||
Image is up to date for busybox@sha256:141c253bc4c3fd0a201d32dc1f493bcf3fff003b6df416dea4f41046e0f37d47
|
||||
```
|
||||
|
||||
<!--
|
||||
2. Create configs for the pod and the container:
|
||||
-->
|
||||
2. 创建 Pod 和容器的配置:
|
||||
|
||||
<!--
|
||||
**Pod config**:
|
||||
-->
|
||||
**Pod 配置**:
|
||||
|
||||
```json
|
||||
{
|
||||
"metadata": {
|
||||
"name": "nginx-sandbox",
|
||||
"namespace": "default",
|
||||
"attempt": 1,
|
||||
"uid": "hdishd83djaidwnduwk28bcsb"
|
||||
},
|
||||
"log_directory": "/tmp",
|
||||
"linux": {
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
<!--
|
||||
**Container config**:
|
||||
-->
|
||||
**容器配置**:
|
||||
|
||||
```json
|
||||
{
|
||||
"metadata": {
|
||||
"name": "busybox"
|
||||
},
|
||||
"image":{
|
||||
"image": "busybox"
|
||||
},
|
||||
"command": [
|
||||
"top"
|
||||
],
|
||||
"log_path":"busybox.log",
|
||||
"linux": {
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
<!--
|
||||
3. Create the container, passing the ID of the previously-created pod, the
|
||||
container config file, and the pod config file. The ID of the container is
|
||||
returned.
|
||||
-->
|
||||
3. 创建容器,传递先前创建的 Pod 的 ID、容器配置文件和 Pod 配置文件。返回容器的 ID。
|
||||
|
||||
```bash
|
||||
crictl create f84dd361f8dc51518ed291fbadd6db537b0496536c1d2d6c05ff943ce8c9a54f container-config.json pod-config.json
|
||||
```
|
||||
|
||||
<!--
|
||||
4. List all containers and verify that the newly-created container has its
|
||||
state set to `Created`.
|
||||
-->
|
||||
4. 查询所有容器并确认新创建的容器状态为 `Created`。
|
||||
|
||||
```bash
|
||||
crictl ps -a
|
||||
```
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```none
|
||||
CONTAINER ID IMAGE CREATED STATE NAME ATTEMPT
|
||||
3e025dd50a72d busybox 32 seconds ago Created busybox 0
|
||||
```
|
||||
|
||||
<!--
|
||||
### Start a container
|
||||
|
||||
To start a container, pass its ID to `crictl start`:
|
||||
-->
|
||||
### 启动容器 {#start-a-container}
|
||||
|
||||
要启动容器,要将容器 ID 传给 `crictl start`:
|
||||
|
||||
```shell
|
||||
crictl start 3e025dd50a72d956c4f14881fbb5b1080c9275674e95fb67f965f6478a957d60
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```
|
||||
3e025dd50a72d956c4f14881fbb5b1080c9275674e95fb67f965f6478a957d60
|
||||
```
|
||||
|
||||
<!--
|
||||
Check the container has its state set to `Running`.
|
||||
-->
|
||||
确认容器的状态为 `Running`。
|
||||
|
||||
```shell
|
||||
crictl ps
|
||||
```
|
||||
|
||||
<!--
|
||||
The output is similar to this:
|
||||
-->
|
||||
输出类似于这样:
|
||||
|
||||
```
|
||||
CONTAINER ID IMAGE CREATED STATE NAME ATTEMPT
|
||||
3e025dd50a72d busybox About a minute ago Running busybox 0
|
||||
```
|
||||
|
||||
## {{% heading "whatsnext" %}}
|
||||
|
||||
<!--
|
||||
* [Learn more about `crictl`](https://github.com/kubernetes-sigs/cri-tools).
|
||||
* [Map `docker` CLI commands to `crictl`](/docs/reference/tools/map-crictl-dockercli/).
|
||||
-->
|
||||
* [进一步了解 `crictl`](https://github.com/kubernetes-sigs/cri-tools)
|
||||
* [将 `docker` CLI 命令映射到 `crictl`](/zh/docs/reference/tools/map-crictl-dockercli/)
|
||||
@@ -0,0 +1,138 @@
|
||||
---
|
||||
title: 使用 telepresence 在本地开发和调试服务
|
||||
content_type: task
|
||||
---
|
||||
|
||||
<!--
|
||||
title: Developing and debugging services locally using telepresence
|
||||
content_type: task
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
{{% thirdparty-content %}}
|
||||
|
||||
<!--
|
||||
Kubernetes applications usually consist of multiple, separate services, each running in its own container. Developing and debugging these services on a remote Kubernetes cluster can be cumbersome, requiring you to [get a shell on a running container](/docs/tasks/debug/debug-application/get-shell-running-container/) in order to run debugging tools.
|
||||
-->
|
||||
|
||||
Kubernetes 应用程序通常由多个独立的服务组成,每个服务都在自己的容器中运行。
|
||||
在远端的 Kubernetes 集群上开发和调试这些服务可能很麻烦,
|
||||
需要[在运行的容器上打开 Shell](/zh/docs/tasks/debug/debug-application/get-shell-running-container/),
|
||||
以运行调试工具。
|
||||
|
||||
<!--
|
||||
`telepresence` is a tool to ease the process of developing and debugging services locally while proxying the service to a remote Kubernetes cluster. Using `telepresence` allows you to use custom tools, such as a debugger and IDE, for a local service and provides the service full access to ConfigMap, secrets, and the services running on the remote cluster.
|
||||
-->
|
||||
|
||||
`telepresence` 是一个工具,用于简化本地开发和调试服务的过程,同时可以将服务代理到远程 Kubernetes 集群。
|
||||
`telepresence` 允许你使用使用自定义工具(例如:调试器 和 IDE)调试服务,
|
||||
并提供对 Configmap、Secret 和远程集群上运行的服务的完全访问。
|
||||
|
||||
|
||||
<!--
|
||||
This document describes using `telepresence` to develop and debug services running on a remote cluster locally.
|
||||
-->
|
||||
本文档描述如何在本地使用 `telepresence` 开发和调试远程集群上运行的服务。
|
||||
|
||||
## {{% heading "prerequisites" %}}
|
||||
|
||||
<!--
|
||||
* Kubernetes cluster is installed
|
||||
* `kubectl` is configured to communicate with the cluster
|
||||
* [Telepresence](https://www.telepresence.io/docs/latest/install/) is installed
|
||||
-->
|
||||
|
||||
* Kubernetes 集群安装完毕
|
||||
* 配置好 `kubectl` 与集群交互
|
||||
* [Telepresence](https://www.telepresence.io/docs/latest/install/) 安装完毕
|
||||
|
||||
<!-- steps -->
|
||||
|
||||
<!--
|
||||
## Connecting your local machine to a remote Kubernetes cluster
|
||||
|
||||
After installing `telepresence`, run `telepresence connect` to launch it's Daemon and connect your local workstation to the cluster.
|
||||
-->
|
||||
|
||||
## 从本机连接到远程 Kubernetes 集群
|
||||
|
||||
安装 `telepresence` 后,运行 `telepresence connect` 来启动它的守护进程并将本地工作站连接到远程 Kubernetes 集群。
|
||||
|
||||
```
|
||||
$ telepresence connect
|
||||
|
||||
Launching Telepresence Daemon
|
||||
...
|
||||
Connected to context default (https://<cluster public IP>)
|
||||
```
|
||||
|
||||
<!--
|
||||
You can curl services using the Kubernetes syntax e.g. `curl -ik https://kubernetes.default`
|
||||
-->
|
||||
|
||||
你可以通过 curl 使用 Kubernetes 语法访问服务,例如:`curl -ik https://kubernetes.default`
|
||||
|
||||
<!--
|
||||
## Developing or debugging an existing service
|
||||
|
||||
When developing an application on Kubernetes, you typically program or debug a single service. The service might require access to other services for testing and debugging. One option is to use the continuous deployment pipeline, but even the fastest deployment pipeline introduces a delay in the program or debug cycle.
|
||||
-->
|
||||
## 开发和调试现有的服务
|
||||
|
||||
在 Kubernetes 上开发应用程序时,通常对单个服务进行编程或调试。
|
||||
服务可能需要访问其他服务以进行测试和调试。
|
||||
一种选择是使用连续部署流水线,但即使最快的部署流水线也会在程序或调试周期中引入延迟。
|
||||
|
||||
<!--
|
||||
Use the `telepresence intercept $SERVICE_NAME --port $LOCAL_PORT:REMOTE_PORT` command to create an "intercept" for rerouting remote service traffic.
|
||||
|
||||
Where:
|
||||
|
||||
- `$SERVICE_NAME` is the name of your local service
|
||||
- `$LOCAL_PORT` is the port that your service is running on your local workstation
|
||||
- And `$REMOTE_PORT` is the port your service listens to in the cluster
|
||||
-->
|
||||
|
||||
使用 `telepresence intercept $SERVICE_NAME --port $LOCAL_PORT:REMOTE_PORT` 命令创建一个 "拦截器" 用于重新路由远程服务流量。
|
||||
|
||||
环境变量:
|
||||
|
||||
- `$SERVICE_NAME` 是本地服务名称
|
||||
- `$LOCAL_PORT` 是服务在本地工作站上运行的端口
|
||||
- `$REMOTE_PORT` 是服务在集群中侦听的端口
|
||||
|
||||
<!--
|
||||
Running this command tells Telepresence to send remote traffic to your local service instead of the service in the remote Kubernetes cluster. Make edits to your service source code locally, save, and see the corresponding changes when accessing your remote application take effect immediately. You can also run your local service using a debugger or any other local development tool.
|
||||
-->
|
||||
|
||||
运行此命令会告诉 Telepresence 将远程流量发送到的本地服务,而不是远程 Kubernetes 集群中的服务中。
|
||||
在本地编辑保存服务源代码,并在访问远程应用时查看相应变更会立即生效。
|
||||
还可以使用调试器或任何其他本地开发工具运行本地服务。
|
||||
|
||||
<!--
|
||||
## How does Telepresence work?
|
||||
|
||||
Telepresence installs a traffic-agent sidecar next to your existing application's container running in the remote cluster. It then captures all traffic requests going into the Pod, and instead of forwarding this to the application in the remote cluster, it routes all traffic (when you create a [global intercept](https://www.getambassador.io/docs/telepresence/latest/concepts/intercepts/#global-intercept)) or a subset of the traffic (when you create a [personal intercept](https://www.getambassador.io/docs/telepresence/latest/concepts/intercepts/#personal-intercept)) to your local development environment.
|
||||
-->
|
||||
|
||||
## Telepresence 是如何工作的?
|
||||
|
||||
Telepresence 会在远程集群中运行的现有应用程序容器旁边安装流量代理 sidecar。
|
||||
当它捕获进入 Pod 的所有流量请求时,不是将其转发到远程集群中的应用程序,
|
||||
而是路由所有流量(当创建[全局拦截器](https://www.getambassador.io/docs/telepresence/latest/concepts/intercepts/#global-intercept)时)
|
||||
或流量的一个子集(当创建[自定义拦截器](https://www.getambassador.io/docs/telepresence/latest/concepts/intercepts/#personal-intercept)时)
|
||||
到本地开发环境。
|
||||
|
||||
## {{% heading "whatsnext" %}}
|
||||
|
||||
<!--
|
||||
If you're interested in a hands-on tutorial, check out [this tutorial](https://cloud.google.com/community/tutorials/developing-services-with-k8s) that walks through locally developing the Guestbook application on Google Kubernetes Engine.
|
||||
-->
|
||||
如果你对实践教程感兴趣,请查看[本教程](https://cloud.google.com/community/tutorials/developing-services-with-k8s),其中介绍了在 Google Kubernetes Engine 上本地开发 Guestbook 应用程序。
|
||||
|
||||
<!--
|
||||
For further reading, visit the [Telepresence website](https://www.telepresence.io).
|
||||
-->
|
||||
|
||||
如需进一步了解,请访问 [Telepresence 官方网站](https://www.telepresence.io)。
|
||||
@@ -0,0 +1,313 @@
|
||||
---
|
||||
content_type: task
|
||||
title: 节点健康监测
|
||||
weight: 20
|
||||
---
|
||||
<!--
|
||||
title: Monitor Node Health
|
||||
content_type: task
|
||||
reviewers:
|
||||
- Random-Liu
|
||||
- dchen1107
|
||||
weight: 20
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
<!--
|
||||
*Node Problem Detector* is a daemon for monitoring and reporting about a node's health.
|
||||
You can run Node Problem Detector as a `DaemonSet` or as a standalone daemon.
|
||||
Node Problem Detector collects information about node problems from various daemons
|
||||
and reports these conditions to the API server as [NodeCondition](/docs/concepts/architecture/nodes/#condition)
|
||||
and [Event](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#event-v1-core).
|
||||
|
||||
To learn how to install and use Node Problem Detector, see
|
||||
[Node Problem Detector project documentation](https://github.com/kubernetes/node-problem-detector).
|
||||
-->
|
||||
|
||||
*节点问题检测器(Node Problem Detector)* 是一个守护程序,用于监视和报告节点的健康状况。
|
||||
你可以将节点问题探测器以 `DaemonSet` 或独立守护程序运行。
|
||||
节点问题检测器从各种守护进程收集节点问题,并以
|
||||
[NodeCondition](/zh/docs/concepts/architecture/nodes/#condition) 和
|
||||
[Event](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#event-v1-core)
|
||||
的形式报告给 API 服务器。
|
||||
|
||||
要了解如何安装和使用节点问题检测器,请参阅
|
||||
[节点问题探测器项目文档](https://github.com/kubernetes/node-problem-detector)。
|
||||
|
||||
## {{% heading "prerequisites" %}}
|
||||
|
||||
{{< include "task-tutorial-prereqs.md" >}}
|
||||
|
||||
<!-- steps -->
|
||||
|
||||
<!--
|
||||
## Limitations
|
||||
|
||||
* Node Problem Detector only supports file based kernel log.
|
||||
Log tools such as `journald` are not supported.
|
||||
|
||||
* Node Problem Detector uses the kernel log format for reporting kernel issues.
|
||||
To learn how to extend the kernel log format, see [Add support for another log format](#support-other-log-format).
|
||||
-->
|
||||
## 局限性 {#limitations}
|
||||
|
||||
* 节点问题检测器只支持基于文件类型的内核日志。
|
||||
它不支持像 journald 这样的命令行日志工具。
|
||||
* 节点问题检测器使用内核日志格式来报告内核问题。
|
||||
要了解如何扩展内核日志格式,请参阅[添加对另一个日志格式的支持](#support-other-log-format)。
|
||||
|
||||
<!--
|
||||
## Enabling Node Problem Detector
|
||||
|
||||
Some cloud providers enable Node Problem Detector as an {{< glossary_tooltip text="Addon" term_id="addons" >}}.
|
||||
You can also enable Node Problem Detector with `kubectl` or by creating an Addon pod.
|
||||
-->
|
||||
## 启用节点问题检测器
|
||||
|
||||
一些云供应商将节点问题检测器以{{< glossary_tooltip text="插件" term_id="addons" >}}形式启用。
|
||||
你还可以使用 `kubectl` 或创建插件 Pod 来启用节点问题探测器。
|
||||
|
||||
<!--
|
||||
## Using kubectl to enable Node Problem Detector {#using-kubectl}
|
||||
|
||||
`kubectl` provides the most flexible management of Node Problem Detector.
|
||||
You can overwrite the default configuration to fit it into your environment or
|
||||
to detect customized node problems. For example:
|
||||
-->
|
||||
## 使用 kubectl 启用节点问题检测器 {#using-kubectl}
|
||||
|
||||
`kubectl` 提供了节点问题探测器最灵活的管理。
|
||||
你可以覆盖默认配置使其适合你的环境或检测自定义节点问题。例如:
|
||||
|
||||
<!--
|
||||
1. Create a Node Problem Detector configuration similar to `node-problem-detector.yaml`:
|
||||
|
||||
{{< codenew file="debug/node-problem-detector.yaml" >}}
|
||||
|
||||
{{< note >}}
|
||||
You should verify that the system log directory is right for your operating system distribution.
|
||||
{{< /note >}}
|
||||
|
||||
1. Start node problem detector with `kubectl`:
|
||||
|
||||
```shell
|
||||
kubectl apply -f https://k8s.io/examples/debug/node-problem-detector.yaml
|
||||
```
|
||||
-->
|
||||
1. 创建类似于 `node-strought-detector.yaml` 的节点问题检测器配置:
|
||||
{{< codenew file="debug/node-problem-detector.yaml" >}}
|
||||
|
||||
{{< note >}}
|
||||
你应该检查系统日志目录是否适用于操作系统发行版本。
|
||||
{{< /note >}}
|
||||
|
||||
1. 使用 `kubectl` 启动节点问题检测器:
|
||||
|
||||
```shell
|
||||
kubectl apply -f https://k8s.io/examples/debug/node-problem-detector.yaml
|
||||
```
|
||||
|
||||
<!--
|
||||
### Using an Addon pod to enable Node Problem Detector {#using-addon-pod}
|
||||
|
||||
If you are using a custom cluster bootstrap solution and don't need
|
||||
to overwrite the default configuration, you can leverage the Addon pod to
|
||||
further automate the deployment.
|
||||
|
||||
Create `node-problem-detector.yaml`, and save the configuration in the Addon pod's
|
||||
directory `/etc/kubernetes/addons/node-problem-detector` on a control plane node.
|
||||
-->
|
||||
### 使用插件 pod 启用节点问题检测器 {#using-addon-pod}
|
||||
|
||||
如果你使用的是自定义集群引导解决方案,不需要覆盖默认配置,
|
||||
可以利用插件 Pod 进一步自动化部署。
|
||||
|
||||
创建 `node-strick-detector.yaml`,并在控制平面节点上保存配置到插件 Pod 的目录
|
||||
`/etc/kubernetes/addons/node-problem-detector`。
|
||||
|
||||
<!--
|
||||
## Overwrite the Configuration
|
||||
|
||||
The [default configuration](https://github.com/kubernetes/node-problem-detector/tree/v0.1/config)
|
||||
is embedded when building the Docker image of Node Problem Detector.
|
||||
-->
|
||||
## 覆盖配置文件
|
||||
|
||||
构建节点问题检测器的 docker 镜像时,会嵌入
|
||||
[默认配置](https://github.com/kubernetes/node-problem-detector/tree/v0.1/config)。
|
||||
|
||||
<!--
|
||||
However, you can use a [`ConfigMap`](/docs/tasks/configure-pod-container/configure-pod-configmap/)
|
||||
to overwrite the configuration:
|
||||
-->
|
||||
不过,你可以像下面这样使用 [`ConfigMap`](/zh/docs/tasks/configure-pod-container/configure-pod-configmap/)
|
||||
将其覆盖:
|
||||
|
||||
<!--
|
||||
1. Change the configuration files in `config/`
|
||||
1. Create the `ConfigMap` `node-problem-detector-config`:
|
||||
|
||||
```shell
|
||||
kubectl create configmap node-problem-detector-config --from-file=config/
|
||||
```
|
||||
|
||||
1. Change the `node-problem-detector.yaml` to use the `ConfigMap`:
|
||||
|
||||
{{< codenew file="debug/node-problem-detector-configmap.yaml" >}}
|
||||
|
||||
1. Recreate the Node Problem Detector with the new configuration file:
|
||||
|
||||
```shell
|
||||
# If you have a node-problem-detector running, delete before recreating
|
||||
kubectl delete -f https://k8s.io/examples/debug/node-problem-detector.yaml
|
||||
kubectl apply -f https://k8s.io/examples/debug/node-problem-detector-configmap.yaml
|
||||
```
|
||||
-->
|
||||
1. 更改 `config/` 中的配置文件
|
||||
1. 创建 `ConfigMap` `node-strick-detector-config`:
|
||||
|
||||
```shell
|
||||
kubectl create configmap node-problem-detector-config --from-file=config/
|
||||
```
|
||||
|
||||
1. 更改 `node-problem-detector.yaml` 以使用 ConfigMap:
|
||||
|
||||
{{< codenew file="debug/node-problem-detector-configmap.yaml" >}}
|
||||
|
||||
1. 使用新的配置文件重新创建节点问题检测器:
|
||||
|
||||
```shell
|
||||
# 如果你正在运行节点问题检测器,请先删除,然后再重新创建
|
||||
kubectl delete -f https://k8s.io/examples/debug/node-problem-detector.yaml
|
||||
kubectl apply -f https://k8s.io/examples/debug/node-problem-detector-configmap.yaml
|
||||
```
|
||||
|
||||
<!--
|
||||
{{< note >}}
|
||||
This approach only applies to a Node Problem Detector started with `kubectl`.
|
||||
{{< /note >}}
|
||||
|
||||
Overwriting a configuration is not supported if a Node Problem Detector runs as a cluster Addon.
|
||||
The Addon manager does not support `ConfigMap`.
|
||||
-->
|
||||
{{< note >}}
|
||||
此方法仅适用于通过 `kubectl` 启动的节点问题检测器。
|
||||
{{< /note >}}
|
||||
|
||||
如果节点问题检测器作为集群插件运行,则不支持覆盖配置。
|
||||
插件管理器不支持 `ConfigMap`。
|
||||
|
||||
<!--
|
||||
## Kernel Monitor
|
||||
|
||||
*Kernel Monitor* is a system log monitor daemon supported in the Node Problem Detector.
|
||||
Kernel monitor watches the kernel log and detects known kernel issues following predefined rules.
|
||||
-->
|
||||
## 内核监视器
|
||||
|
||||
*内核监视器(Kernel Monitor)* 是节点问题检测器中支持的系统日志监视器守护进程。
|
||||
内核监视器观察内核日志并根据预定义规则检测已知的内核问题。
|
||||
|
||||
<!--
|
||||
The Kernel Monitor matches kernel issues according to a set of predefined rule list in
|
||||
[`config/kernel-monitor.json`](https://github.com/kubernetes/node-problem-detector/blob/v0.1/config/kernel-monitor.json). The rule list is extensible. You can expand the rule list by overwriting the
|
||||
configuration.
|
||||
-->
|
||||
内核监视器根据 [`config/kernel-monitor.json`](https://github.com/kubernetes/node-problem-detector/blob/v0.1/config/kernel-monitor.json)
|
||||
中的一组预定义规则列表匹配内核问题。
|
||||
规则列表是可扩展的,你始终可以通过覆盖配置来扩展它。
|
||||
|
||||
<!--
|
||||
### Add new NodeConditions
|
||||
|
||||
To support a new `NodeCondition`, create a condition definition within the `conditions` field in
|
||||
`config/kernel-monitor.json`, for example:
|
||||
```
|
||||
-->
|
||||
### 添加新的 NodeCondition
|
||||
|
||||
要支持新的 `NodeCondition`,请在 `config/kernel-monitor.json` 中的
|
||||
`conditions` 字段中创建一个条件定义:
|
||||
|
||||
```json
|
||||
{
|
||||
"type": "NodeConditionType",
|
||||
"reason": "CamelCaseDefaultNodeConditionReason",
|
||||
"message": "arbitrary default node condition message"
|
||||
}
|
||||
```
|
||||
|
||||
<!--
|
||||
### Detect new problems
|
||||
|
||||
To detect new problems, you can extend the `rules` field in `config/kernel-monitor.json`
|
||||
with a new rule definition:
|
||||
-->
|
||||
### 检测新的问题
|
||||
|
||||
你可以使用新的规则描述来扩展 `config/kernel-monitor.json` 中的 `rules` 字段以检测新问题:
|
||||
|
||||
```json
|
||||
{
|
||||
"type": "temporary/permanent",
|
||||
"condition": "NodeConditionOfPermanentIssue",
|
||||
"reason": "CamelCaseShortReason",
|
||||
"message": "regexp matching the issue in the kernel log"
|
||||
}
|
||||
```
|
||||
|
||||
<!--
|
||||
### Configure path for the kernel log device {#kernel-log-device-path}
|
||||
|
||||
Check your kernel log path location in your operating system (OS) distribution.
|
||||
The Linux kernel [log device](https://www.kernel.org/doc/Documentation/ABI/testing/dev-kmsg) is usually presented as `/dev/kmsg`. However, the log path location varies by OS distribution.
|
||||
The `log` field in `config/kernel-monitor.json` represents the log path inside the container.
|
||||
You can configure the `log` field to match the device path as seen by the Node Problem Detector.
|
||||
-->
|
||||
### 配置内核日志设备的路径 {#kernel-log-device-path}
|
||||
|
||||
检查你的操作系统(OS)发行版本中的内核日志路径位置。
|
||||
Linux 内核[日志设备](https://www.kernel.org/doc/documentation/abi/testing/dev-kmsg)
|
||||
通常呈现为 `/dev/kmsg`。
|
||||
但是,日志路径位置因 OS 发行版本而异。
|
||||
`config/kernel-monitor.json` 中的 `log` 字段表示容器内的日志路径。
|
||||
你可以配置 `log` 字段以匹配节点问题检测器所示的设备路径。
|
||||
|
||||
<!--
|
||||
### Add support for another log format {#support-other-log-format}
|
||||
|
||||
Kernel monitor uses the
|
||||
[`Translator`](https://github.com/kubernetes/node-problem-detector/blob/v0.1/pkg/kernelmonitor/translator/translator.go) plugin to translate the internal data structure of the kernel log.
|
||||
You can implement a new translator for a new log format.
|
||||
-->
|
||||
### 添加对其它日志格式的支持 {#support-other-log-format}
|
||||
|
||||
内核监视器使用
|
||||
[`Translator`](https://github.com/kubernetes/node-problem-detector/blob/v0.1/pkg/kernelmonitor/translator.go)
|
||||
插件转换内核日志的内部数据结构。
|
||||
你可以为新的日志格式实现新的转换器。
|
||||
|
||||
<!-- discussion -->
|
||||
|
||||
<!--
|
||||
## Recommendations and restrictions
|
||||
|
||||
It is recommended to run the Node Problem Detector in your cluster to monitor node health.
|
||||
When running the Node Problem Detector, you can expect extra resource overhead on each node.
|
||||
Usually this is fine, because:
|
||||
|
||||
* The kernel log grows relatively slowly.
|
||||
* A resource limit is set for the Node Problem Detector.
|
||||
* Even under high load, the resource usage is acceptable. For more information, see the Node Problem Detector
|
||||
[benchmark result](https://github.com/kubernetes/node-problem-detector/issues/2#issuecomment-220255629).
|
||||
-->
|
||||
## 建议和限制
|
||||
|
||||
建议在集群中运行节点问题检测器以监控节点运行状况。
|
||||
运行节点问题检测器时,你可以预期每个节点上的额外资源开销。
|
||||
通常这是可接受的,因为:
|
||||
|
||||
* 内核日志增长相对缓慢。
|
||||
* 已经为节点问题检测器设置了资源限制。
|
||||
* 即使在高负载下,资源使用也是可接受的。有关更多信息,请参阅节点问题检测器
|
||||
[基准结果](https://github.com/kubernetes/node-problem-detector/issues/2.suecomment-220255629)。
|
||||
@@ -0,0 +1,419 @@
|
||||
---
|
||||
title: 资源指标管道
|
||||
content_type: concept
|
||||
weight: 15
|
||||
---
|
||||
<!--
|
||||
reviewers:
|
||||
- fgrzadkowski
|
||||
- piosz
|
||||
title: Resource metrics pipeline
|
||||
content_type: concept
|
||||
weight: 15
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
<!--
|
||||
For Kubernetes, the _Metrics API_ offers a basic set of metrics to support automatic scaling and
|
||||
similar use cases. This API makes information available about resource usage for node and pod,
|
||||
including metrics for CPU and memory. If you deploy the Metrics API into your cluster, clients of
|
||||
the Kubernetes API can then query for this information, and you can use Kubernetes' access control
|
||||
mechanisms to manage permissions to do so.
|
||||
|
||||
The [HorizontalPodAutoscaler](/docs/tasks/run-application/horizontal-pod-autoscale/) (HPA) and
|
||||
[VerticalPodAutoscaler](https://github.com/kubernetes/autoscaler/tree/master/vertical-pod-autoscaler#readme) (VPA)
|
||||
use data from the metrics API to adjust workload replicas and resources to meet customer demand.
|
||||
|
||||
You can also view the resource metrics using the
|
||||
[`kubectl top`](/docs/reference/generated/kubectl/kubectl-commands#top)
|
||||
command.
|
||||
-->
|
||||
|
||||
对于 Kubernetes,_Metrics API_ 提供了一组基本的指标,以支持自动伸缩和类似的用例。
|
||||
该 API 提供有关节点和 Pod 的资源使用情况的信息,
|
||||
包括 CPU 和内存的指标。如果将 Metrics API 部署到集群中,
|
||||
那么 Kubernetes API 的客户端就可以查询这些信息,并且可以使用 Kubernetes 的访问控制机制来管理权限。
|
||||
|
||||
[HorizontalPodAutoscaler](/zh/docs/tasks/run-application/horizontal-pod-autoscale/) (HPA) 和
|
||||
[VerticalPodAutoscaler](https://github.com/kubernetes/autoscaler/tree/master/vertical-pod-autoscaler#readme) (VPA)
|
||||
使用 metrics API 中的数据调整工作负载副本和资源,以满足客户需求。
|
||||
|
||||
你也可以通过 [`kubectl top`](/zh/docs/reference/generated/kubectl/kubectl-commands#top) 命令来查看资源指标。
|
||||
|
||||
{{< note >}}
|
||||
<!--
|
||||
The Metrics API, and the metrics pipeline that it enables, only offers the minimum
|
||||
CPU and memory metrics to enable automatic scaling using HPA and / or VPA.
|
||||
If you would like to provide a more complete set of metrics, you can complement
|
||||
the simpler Metrics API by deploying a second
|
||||
[metrics pipeline](/docs/tasks/debug/debug-cluster/resource-usage-monitoring/#full-metrics-pipeline)
|
||||
that uses the _Custom Metrics API_.
|
||||
-->
|
||||
Metrics API 及其启用的指标管道仅提供最少的 CPU 和内存指标,以启用使用 HPA 和/或 VPA 的自动扩展。
|
||||
如果你想提供更完整的指标集,你可以通过部署使用 _Custom Metrics API_ 的第二个
|
||||
[指标管道](/zh/docs/tasks/debug/debug-cluster/resource-usage-monitoring/#full-metrics-pipeline)来作为简单的 Metrics API 的补充。
|
||||
{{< /note >}}
|
||||
|
||||
<!--
|
||||
Figure 1 illustrates the architecture of the resource metrics pipeline.
|
||||
-->
|
||||
图 1 说明了资源指标管道的架构。
|
||||
|
||||
{{< mermaid >}}
|
||||
flowchart RL
|
||||
subgraph cluster[Cluster]
|
||||
direction RL
|
||||
S[ <br><br> ]
|
||||
A[Metrics-<br>Server]
|
||||
subgraph B[Nodes]
|
||||
direction TB
|
||||
D[cAdvisor] --> C[kubelet]
|
||||
E[Container<br>runtime] --> D
|
||||
E1[Container<br>runtime] --> D
|
||||
P[pod data] -.- C
|
||||
end
|
||||
L[API<br>server]
|
||||
W[HPA]
|
||||
C ---->|Summary<br>API| A -->|metrics<br>API| L --> W
|
||||
end
|
||||
L ---> K[kubectl<br>top]
|
||||
classDef box fill:#fff,stroke:#000,stroke-width:1px,color:#000;
|
||||
class W,B,P,K,cluster,D,E,E1 box
|
||||
classDef spacewhite fill:#ffffff,stroke:#fff,stroke-width:0px,color:#000
|
||||
class S spacewhite
|
||||
classDef k8s fill:#326ce5,stroke:#fff,stroke-width:1px,color:#fff;
|
||||
class A,L,C k8s
|
||||
{{< /mermaid >}}
|
||||
|
||||
<!--
|
||||
Figure 1. Resource Metrics Pipeline
|
||||
|
||||
The architecture components, from right to left in the figure, consist of the following:
|
||||
|
||||
* [cAdvisor](https://github.com/google/cadvisor): Daemon for collecting, aggregating and exposing
|
||||
container metrics included in Kubelet.
|
||||
* [kubelet](/docs/concepts/overview/components/#kubelet): Node agent for managing container
|
||||
resources. Resource metrics are accessible using the `/metrics/resource` and `/stats` kubelet
|
||||
API endpoints.
|
||||
* [Summary API](#summary-api-source): API provided by the kubelet for discovering and retrieving
|
||||
per-node summarized stats available through the `/stats` endpoint.
|
||||
* [metrics-server](#metrics-server): Cluster addon component that collects and aggregates resource
|
||||
metrics pulled from each kubelet. The API server serves Metrics API for use by HPA, VPA, and by
|
||||
the `kubectl top` command. Metrics Server is a reference implementation of the Metrics API.
|
||||
* [Metrics API](#metrics-api): Kubernetes API supporting access to CPU and memory used for
|
||||
workload autoscaling. To make this work in your cluster, you need an API extension server that
|
||||
provides the Metrics API.
|
||||
-->
|
||||
图 1. 资源指标管道
|
||||
|
||||
图中从右到左的架构组件包括以下内容:
|
||||
|
||||
* [cAdvisor](https://github.com/google/cadvisor): 用于收集、聚合和公开 Kubelet 中包含的容器指标的守护程序。
|
||||
* [kubelet](/zh/docs/concepts/overview/components/#kubelet): 用于管理容器资源的节点代理。
|
||||
可以使用 `/metrics/resource` 和 `/stats` kubelet API 端点访问资源指标。
|
||||
* [Summary API](#summary-api-source): kubelet 提供的 API,用于发现和检索可通过 `/stats` 端点获得的每个节点的汇总统计信息。
|
||||
* [metrics-server](#metrics-server): 集群插件组件,用于收集和聚合从每个 kubelet 中提取的资源指标。
|
||||
API 服务器提供 Metrics API 以供 HPA、VPA 和 `kubectl top` 命令使用。 Metrics Server 是 Metrics API 的参考实现。
|
||||
* [Metrics API](#metrics-api): Kubernetes API 支持访问用于工作负载自动缩放的 CPU 和内存。
|
||||
要在你的集群中进行这项工作,你需要一个提供 Metrics API 的 API 扩展服务器。
|
||||
|
||||
<!--
|
||||
cAdvisor supports reading metrics from cgroups, which works with typical container runtimes on Linux.
|
||||
If you use a container runtime that uses another resource isolation mechanism, for example
|
||||
virtualization, then that container runtime must support
|
||||
[CRI Container Metrics](https://github.com/kubernetes/community/blob/master/contributors/devel/sig-node/cri-container-stats.md)
|
||||
in order for metrics to be available to the kubelet.
|
||||
-->
|
||||
{{< note >}}
|
||||
cAdvisor 支持从 cgroups 读取指标,它适用于 Linux 上的典型容器运行时。
|
||||
如果你使用基于其他资源隔离机制的容器运行时,例如虚拟化,那么该容器运行时必须支持
|
||||
[CRI 容器指标](https://github.com/kubernetes/community/blob/master/contributors/devel/sig-node/cri-container-stats.md)
|
||||
以便 kubelet 可以使用指标。
|
||||
{{< /note >}}
|
||||
|
||||
<!-- body -->
|
||||
|
||||
<!--
|
||||
## Metrics API
|
||||
|
||||
The metrics-server implements the Metrics API. This API allows you to access CPU and memory usage
|
||||
for the nodes and pods in your cluster. Its primary role is to feed resource usage metrics to K8s
|
||||
autoscaler components.
|
||||
|
||||
Here is an example of the Metrics API request for a `minikube` node piped through `jq` for easier
|
||||
reading:
|
||||
|
||||
-->
|
||||
## Metrics API {#the-metrics-api}
|
||||
|
||||
{{< feature-state for_k8s_version="1.8" state="beta" >}}
|
||||
|
||||
metrics-server 实现了 Metrics API。此 API 允许你访问集群中节点和 Pod 的 CPU 和内存使用情况。
|
||||
它的主要作用是将资源使用指标提供给 K8s 自动缩放器组件。
|
||||
|
||||
下面是一个 `minikube` 节点的 Metrics API 请求示例,通过 `jq` 管道处理以便于阅读:
|
||||
|
||||
```shell
|
||||
kubectl get --raw "/apis/metrics.k8s.io/v1beta1/nodes/minikube" | jq '.'
|
||||
```
|
||||
|
||||
<!-- Here is the same API call using `curl`: -->
|
||||
这是使用 `curl` 来执行的相同 API 调用:
|
||||
|
||||
```shell
|
||||
curl http://localhost:8080/apis/metrics.k8s.io/v1beta1/nodes/minikube
|
||||
```
|
||||
|
||||
<!-- Sample response: -->
|
||||
响应示例:
|
||||
|
||||
```json
|
||||
{
|
||||
"kind": "NodeMetrics",
|
||||
"apiVersion": "metrics.k8s.io/v1beta1",
|
||||
"metadata": {
|
||||
"name": "minikube",
|
||||
"selfLink": "/apis/metrics.k8s.io/v1beta1/nodes/minikube",
|
||||
"creationTimestamp": "2022-01-27T18:48:43Z"
|
||||
},
|
||||
"timestamp": "2022-01-27T18:48:33Z",
|
||||
"window": "30s",
|
||||
"usage": {
|
||||
"cpu": "487558164n",
|
||||
"memory": "732212Ki"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
<!--
|
||||
Here is an example of the Metrics API request for a `kube-scheduler-minikube` pod contained in the
|
||||
`kube-system` namespace and piped through `jq` for easier reading:
|
||||
-->
|
||||
|
||||
下面是一个 `kube-system` 命名空间中的 `kube-scheduler-minikube` Pod 的 Metrics API 请求示例,
|
||||
通过 `jq` 管道处理以便于阅读:
|
||||
|
||||
```shell
|
||||
kubectl get --raw "/apis/metrics.k8s.io/v1beta1/namespaces/kube-system/pods/kube-scheduler-minikube" | jq '.'
|
||||
```
|
||||
|
||||
<!-- Here is the same API call using `curl`: -->
|
||||
这是使用 `curl` 来完成的相同 API 调用:
|
||||
|
||||
```shell
|
||||
curl http://localhost:8080/apis/metrics.k8s.io/v1beta1/namespaces/kube-system/pods/kube-scheduler-minikube
|
||||
```
|
||||
|
||||
<!-- Sample response: -->
|
||||
响应示例:
|
||||
|
||||
```json
|
||||
{
|
||||
"kind": "PodMetrics",
|
||||
"apiVersion": "metrics.k8s.io/v1beta1",
|
||||
"metadata": {
|
||||
"name": "kube-scheduler-minikube",
|
||||
"namespace": "kube-system",
|
||||
"selfLink": "/apis/metrics.k8s.io/v1beta1/namespaces/kube-system/pods/kube-scheduler-minikube",
|
||||
"creationTimestamp": "2022-01-27T19:25:00Z"
|
||||
},
|
||||
"timestamp": "2022-01-27T19:24:31Z",
|
||||
"window": "30s",
|
||||
"containers": [
|
||||
{
|
||||
"name": "kube-scheduler",
|
||||
"usage": {
|
||||
"cpu": "9559630n",
|
||||
"memory": "22244Ki"
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
<!--
|
||||
The Metrics API is defined in the [k8s.io/metrics](https://github.com/kubernetes/metrics)
|
||||
repository. You must enable the [API aggregation layer](/docs/tasks/extend-kubernetes/configure-aggregation-layer/)
|
||||
and register an [APIService](/docs/reference/kubernetes-api/cluster-resources/api-service-v1/)
|
||||
for the `metrics.k8s.io` API.
|
||||
|
||||
To learn more about the Metrics API, see [resource metrics API design](https://github.com/kubernetes/design-proposals-archive/blob/main/instrumentation/resource-metrics-api.md),
|
||||
the [metrics-server repository](https://github.com/kubernetes-sigs/metrics-server) and the
|
||||
[resource metrics API](https://github.com/kubernetes/metrics#resource-metrics-api).
|
||||
-->
|
||||
|
||||
Metrics API 在 [k8s.io/metrics](https://github.com/kubernetes/metrics) 代码库中定义。
|
||||
你必须启用 [API 聚合层](/zh/docs/tasks/extend-kubernetes/configure-aggregation-layer/)并为
|
||||
`metrics.k8s.io` API 注册一个 [APIService](/zh/docs/reference/kubernetes-api/cluster-resources/api-service-v1/)。
|
||||
|
||||
要了解有关 Metrics API 的更多信息,
|
||||
请参阅资源 [Resource Metrics API Design](https://github.com/kubernetes/design-proposals-archive/blob/main/instrumentation/resource-metrics-api.md)、
|
||||
[metrics-server 代码库](https://github.com/kubernetes-sigs/metrics-server) 和
|
||||
[Resource Metrics API](https://github.com/kubernetes/metrics#resource-metrics-api)。
|
||||
|
||||
<!--
|
||||
You must deploy the metrics-server or alternative adapter that serves the Metrics API to be able
|
||||
to access it.
|
||||
-->
|
||||
{{< note >}}
|
||||
你必须部署提供 Metrics API 服务的 metrics-server 或其他适配器才能访问它。
|
||||
{{< /note >}}
|
||||
|
||||
<!--
|
||||
## Measuring Resource Usage
|
||||
|
||||
### CPU
|
||||
|
||||
CPU is reported as the average core usage measured in cpu units. One cpu, in Kubernetes, is
|
||||
equivalent to 1 vCPU/Core for cloud providers, and 1 hyper-thread on bare-metal Intel processors.
|
||||
|
||||
This value is derived by taking a rate over a cumulative CPU counter provided by the kernel (in
|
||||
both Linux and Windows kernels). The time window used to calculate CPU is shown under window field
|
||||
in Metrics API.
|
||||
|
||||
To learn more about how Kubernetes allocates and measures CPU resources, see
|
||||
[meaning of CPU](/docs/concepts/configuration/manage-resources-containers/#meaning-of-cpu).
|
||||
-->
|
||||
## 度量资源用量 {#measuring-resource-usage}
|
||||
|
||||
### CPU
|
||||
|
||||
CPU 报告为以 cpu 为单位测量的平均核心使用率。在 Kubernetes 中,
|
||||
一个 cpu 相当于云提供商的 1 个 vCPU/Core,以及裸机 Intel 处理器上的 1 个超线程。
|
||||
|
||||
该值是通过对内核提供的累积 CPU 计数器(在 Linux 和 Windows 内核中)取一个速率得出的。
|
||||
用于计算 CPU 的时间窗口显示在 Metrics API 的窗口字段下。
|
||||
|
||||
要了解更多关于 Kubernetes 如何分配和测量 CPU 资源的信息,请参阅
|
||||
[CPU 的含义](/zh/docs/concepts/configuration/manage-resources-containers/#meaning-of-cpu)。
|
||||
|
||||
<!--
|
||||
### Memory
|
||||
|
||||
Memory is reported as the working set, measured in bytes, at the instant the metric was collected.
|
||||
|
||||
In an ideal world, the "working set" is the amount of memory in-use that cannot be freed under
|
||||
memory pressure. However, calculation of the working set varies by host OS, and generally makes
|
||||
heavy use of heuristics to produce an estimate.
|
||||
|
||||
The Kubernetes model for a container's working set expects that the container runtime counts
|
||||
anonymous memory associated with the container in question. The working set metric typically also
|
||||
includes some cached (file-backed) memory, because the host OS cannot always reclaim pages.
|
||||
|
||||
To learn more about how Kubernetes allocates and measures memory resources, see
|
||||
[meaning of memory](/docs/concepts/configuration/manage-resources-containers/#meaning-of-memory).
|
||||
-->
|
||||
### 内存 {#memory}
|
||||
|
||||
内存报告为在收集度量标准的那一刻的工作集大小,以字节为单位。
|
||||
|
||||
在理想情况下,“工作集”是在内存压力下无法释放的正在使用的内存量。
|
||||
然而,工作集的计算因主机操作系统而异,并且通常大量使用启发式算法来产生估计。
|
||||
|
||||
Kubernetes 模型中,容器工作集是由容器运行时计算的与相关容器关联的匿名内存。
|
||||
工作集指标通常还包括一些缓存(文件支持)内存,因为主机操作系统不能总是回收页面。
|
||||
|
||||
要了解有关 Kubernetes 如何分配和测量内存资源的更多信息,
|
||||
请参阅[内存的含义](/zh/docs/concepts/configuration/manage-resources-containers/#meaning-of-memory)。
|
||||
|
||||
<!--
|
||||
## Metrics Server
|
||||
|
||||
The metrics-server fetches resource metrics from the kubelets and exposes them in the Kubernetes
|
||||
API server through the Metrics API for use by the HPA and VPA. You can also view these metrics
|
||||
using the `kubectl top` command.
|
||||
|
||||
The metrics-server uses the Kubernetes API to track nodes and pods in your cluster. The
|
||||
metrics-server queries each node over HTTP to fetch metrics. The metrics-server also builds an
|
||||
internal view of pod metadata, and keeps a cache of pod health. That cached pod health information
|
||||
is available via the extension API that the metrics-server makes available.
|
||||
|
||||
For example with an HPA query, the metrics-server needs to identify which pods fulfill the label
|
||||
selectors in the deployment.
|
||||
-->
|
||||
## Metrics 服务器 {#metrics-server}
|
||||
|
||||
metrics-server 从 kubelet 中获取资源指标,并通过 Metrics API 在 Kubernetes API 服务器中公开它们,以供 HPA 和 VPA 使用。
|
||||
你还可以使用 `kubectl top` 命令查看这些指标。
|
||||
|
||||
metrics-server 使用 Kubernetes API 来跟踪集群中的节点和 Pod。metrics-server 服务器通过 HTTP 查询每个节点以获取指标。
|
||||
metrics-server 还构建了 Pod 元数据的内部视图,并维护 Pod 健康状况的缓存。
|
||||
缓存的 Pod 健康信息可通过 metrics-server 提供的扩展 API 获得。
|
||||
|
||||
例如,对于 HPA 查询,metrics-server 需要确定哪些 Pod 满足 Deployment 中的标签选择器。
|
||||
|
||||
<!--
|
||||
The metrics-server calls the [kubelet](/docs/reference/command-line-tools-reference/kubelet/) API
|
||||
to collect metrics from each node. Depending on the metrics-server version it uses:
|
||||
|
||||
* Metrics resource endpoint `/metrics/resource` in version v0.6.0+ or
|
||||
* Summary API endpoint `/stats/summary` in older versions
|
||||
-->
|
||||
metrics-server 调用 [kubelet](/zh/docs/reference/command-line-tools-reference/kubelet/) API
|
||||
从每个节点收集指标。根据它使用的度量服务器版本:
|
||||
|
||||
* 版本 v0.6.0+ 中,使用指标资源端点 `/metrics/resource`
|
||||
* 旧版本中使用 Summary API 端点 `/stats/summary`
|
||||
|
||||
<!--
|
||||
To learn more about the metrics-server, see the
|
||||
[metrics-server repository](https://github.com/kubernetes-sigs/metrics-server).
|
||||
|
||||
You can also check out the following:
|
||||
|
||||
* [metrics-server design](https://github.com/kubernetes/community/blob/master/contributors/design-proposals/instrumentation/metrics-server.md)
|
||||
* [metrics-server FAQ](https://github.com/kubernetes-sigs/metrics-server/blob/master/FAQ.md)
|
||||
* [metrics-server known issues](https://github.com/kubernetes-sigs/metrics-server/blob/master/KNOWN_ISSUES.md)
|
||||
* [metrics-server releases](https://github.com/kubernetes-sigs/metrics-server/releases)
|
||||
* [Horizontal Pod Autoscaling](/docs/tasks/run-application/horizontal-pod-autoscale/)
|
||||
-->
|
||||
|
||||
了解更多 metrics-server,参阅 [metrics-server 代码库](https://github.com/kubernetes-sigs/metrics-server)。
|
||||
|
||||
你还可以查看以下内容:
|
||||
|
||||
* [metrics-server 设计](https://github.com/kubernetes/community/blob/master/contributors/design-proposals/instrumentation/metrics-server.md)
|
||||
* [metrics-server FAQ](https://github.com/kubernetes-sigs/metrics-server/blob/master/FAQ.md)
|
||||
* [metrics-server known issues](https://github.com/kubernetes-sigs/metrics-server/blob/master/KNOWN_ISSUES.md)
|
||||
* [metrics-server releases](https://github.com/kubernetes-sigs/metrics-server/releases)
|
||||
* [Horizontal Pod Autoscaling](/zh/docs/tasks/run-application/horizontal-pod-autoscale/)
|
||||
|
||||
<!--
|
||||
### Summary API Source
|
||||
|
||||
The [Kubelet](/docs/reference/command-line-tools-reference/kubelet/) gathers stats at node, volume, pod and container level, and emits
|
||||
them in the [Summary API](https://github.com/kubernetes/kubernetes/blob/7d309e0104fedb57280b261e5677d919cb2a0e2d/staging/src/k8s.io/kubelet/pkg/apis/stats/v1alpha1/types.go)
|
||||
for consumers to read.
|
||||
-->
|
||||
|
||||
### Summary API 来源
|
||||
|
||||
[Kubelet](/zh/docs/reference/command-line-tools-reference/kubelet/) 在节点、卷、Pod 和容器级别收集统计信息,
|
||||
并在[Summary API](https://github.com/kubernetes/kubernetes/blob/7d309e0104fedb57280b261e5677d919cb2a0e2d/staging/src/k8s.io/kubelet/pkg/apis/stats/v1alpha1/types.go)
|
||||
中提供它们的统计信息供消费者阅读。
|
||||
|
||||
<!--
|
||||
Here is an example of a Summary API request for a `minikube` node:
|
||||
-->
|
||||
|
||||
下面是一个 `minikube` 节点的 Summary API 请求示例:
|
||||
|
||||
```shell
|
||||
kubectl get --raw "/api/v1/nodes/minikube/proxy/stats/summary"
|
||||
```
|
||||
|
||||
<!-- Here is the same API call using `curl`: -->
|
||||
这是使用 `curl` 来执行的相同 API 调用:
|
||||
|
||||
```shell
|
||||
curl http://localhost:8080/api/v1/nodes/minikube/proxy/stats/summary
|
||||
```
|
||||
|
||||
{{< note >}}
|
||||
<!--
|
||||
The summary API `/stats/summary` endpoint will be replaced by the `/metrics/resource` endpoint
|
||||
beginning with metrics-server 0.6.x.
|
||||
-->
|
||||
从 metrics-server 0.6.x 开始,Summary API `/stats/summary` 端点被 `/metrics/resource` 端点替换。
|
||||
{{< /note >}}
|
||||
@@ -0,0 +1,113 @@
|
||||
---
|
||||
content_type: concept
|
||||
title: 资源监控工具
|
||||
---
|
||||
<!--
|
||||
reviewers:
|
||||
- mikedanese
|
||||
content_type: concept
|
||||
title: Tools for Monitoring Resources
|
||||
-->
|
||||
|
||||
<!-- overview -->
|
||||
|
||||
<!--
|
||||
To scale an application and provide a reliable service, you need to
|
||||
understand how the application behaves when it is deployed. You can examine
|
||||
application performance in a Kubernetes cluster by examining the containers,
|
||||
[pods](/docs/concepts/workloads/pods/),
|
||||
[services](/docs/concepts/services-networking/service/), and
|
||||
the characteristics of the overall cluster. Kubernetes provides detailed
|
||||
information about an application's resource usage at each of these levels.
|
||||
This information allows you to evaluate your application's performance and
|
||||
where bottlenecks can be removed to improve overall performance.
|
||||
-->
|
||||
要扩展应用程序并提供可靠的服务,你需要了解应用程序在部署时的行为。
|
||||
你可以通过检测容器检查 Kubernetes 集群中的应用程序性能,
|
||||
[Pods](/zh/docs/concepts/workloads/pods),
|
||||
[服务](/zh/docs/concepts/services-networking/service/)
|
||||
和整个集群的特征。
|
||||
Kubernetes 在每个级别上提供有关应用程序资源使用情况的详细信息。
|
||||
此信息使你可以评估应用程序的性能,以及在何处可以消除瓶颈以提高整体性能。
|
||||
|
||||
<!-- body -->
|
||||
|
||||
<!--
|
||||
In Kubernetes, application monitoring does not depend on a single monitoring solution.
|
||||
On new clusters, you can use [resource metrics](#resource-metrics-pipeline) or
|
||||
[full metrics](#full-metrics-pipeline) pipelines to collect monitoring statistics.
|
||||
-->
|
||||
在 Kubernetes 中,应用程序监控不依赖单个监控解决方案。
|
||||
在新集群上,你可以使用[资源度量](#resource-metrics-pipeline)或
|
||||
[完整度量](#full-metrics-pipeline)管道来收集监视统计信息。
|
||||
|
||||
<!--
|
||||
## Resource metrics pipeline
|
||||
|
||||
The resource metrics pipeline provides a limited set of metrics related to
|
||||
cluster components such as the
|
||||
[Horizontal Pod Autoscaler](/docs/tasks/run-application/horizontal-pod-autoscale)
|
||||
controller, as well as the `kubectl top` utility.
|
||||
These metrics are collected by the lightweight, short-term, in-memory
|
||||
[metrics-server](https://github.com/kubernetes-sigs/metrics-server) and
|
||||
are exposed via the `metrics.k8s.io` API.
|
||||
-->
|
||||
## 资源度量管道 {#resource-metrics-pipeline}
|
||||
|
||||
资源指标管道提供了一组与集群组件,例如
|
||||
[Horizontal Pod Autoscaler](/zh/docs/tasks/run-application/horizontal-pod-autoscale/)
|
||||
控制器以及 `kubectl top` 实用程序相关的有限度量。
|
||||
这些指标是由轻量级的、短期、内存存储的
|
||||
[metrics-server](https://github.com/kubernetes-sigs/metrics-server) 收集的,
|
||||
通过 `metrics.k8s.io` 公开。
|
||||
|
||||
<!--
|
||||
metrics-server discovers all nodes on the cluster and
|
||||
queries each node's
|
||||
[kubelet](/docs/reference/command-line-tools-reference/kubelet/) for CPU and
|
||||
memory usage. The kubelet acts as a bridge between the Kubernetes master and
|
||||
the nodes, managing the pods and containers running on a machine. The kubelet
|
||||
translates each pod into its constituent containers and fetches individual
|
||||
container usage statistics from the container runtime through the container
|
||||
runtime interface. The kubelet fetches this information from the integrated
|
||||
cAdvisor for the legacy Docker integration. It then exposes the aggregated pod
|
||||
resource usage statistics through the metrics-server Resource Metrics API.
|
||||
This API is served at `/metrics/resource/v1beta1` on the kubelet's authenticated and
|
||||
read-only ports.
|
||||
-->
|
||||
度量服务器发现集群中的所有节点,并且查询每个节点的
|
||||
[kubelet](/zh/docs/reference/command-line-tools-reference/kubelet/)
|
||||
以获取 CPU 和内存使用情况。
|
||||
Kubelet 充当 Kubernetes 主节点与节点之间的桥梁,管理机器上运行的 Pod 和容器。
|
||||
kubelet 将每个 Pod 转换为其组成的容器,并在容器运行时通过容器运行时接口
|
||||
获取各个容器使用情况统计信息。
|
||||
kubelet 从集成的 cAdvisor 获取此信息,以进行旧式 Docker 集成。
|
||||
然后,它通过 metrics-server Resource Metrics API 公开聚合的 pod 资源使用情况统计信息。
|
||||
该 API 在 kubelet 的经过身份验证和只读的端口上的 `/metrics/resource/v1beta1` 中提供。
|
||||
|
||||
<!--
|
||||
## Full metrics pipeline
|
||||
|
||||
A full metrics pipeline gives you access to richer metrics. Kubernetes can
|
||||
respond to these metrics by automatically scaling or adapting the cluster
|
||||
based on its current state, using mechanisms such as the Horizontal Pod
|
||||
Autoscaler. The monitoring pipeline fetches metrics from the kubelet and
|
||||
then exposes them to Kubernetes via an adapter by implementing either the
|
||||
`custom.metrics.k8s.io` or `external.metrics.k8s.io` API.
|
||||
-->
|
||||
## 完整度量管道 {#full-metrics-pipeline}
|
||||
|
||||
一个完整度量管道可以让你访问更丰富的度量。
|
||||
Kubernetes 还可以根据集群的当前状态,使用 Pod 水平自动扩缩器等机制,
|
||||
通过自动调用扩展或调整集群来响应这些度量。
|
||||
监控管道从 kubelet 获取度量值,然后通过适配器将它们公开给 Kubernetes,
|
||||
方法是实现 `custom.metrics.k8s.io` 或 `external.metrics.k8s.io` API。
|
||||
|
||||
<!--
|
||||
[Prometheus](https://prometheus.io), a CNCF project, can natively monitor Kubernetes, nodes, and Prometheus itself.
|
||||
Full metrics pipeline projects that are not part of the CNCF are outside the scope of Kubernetes documentation.
|
||||
-->
|
||||
[Prometheus](https://prometheus.io) 是一个 CNCF 项目,可以原生监控 Kubernetes、
|
||||
节点和 Prometheus 本身。
|
||||
完整度量管道项目不属于 CNCF 的一部分,不在 Kubernetes 文档的范围之内。
|
||||
|
||||
@@ -0,0 +1,314 @@
|
||||
---
|
||||
title: Windows 调试小技巧
|
||||
content_type: concept
|
||||
---
|
||||
<!--
|
||||
title: Windows debugging tips
|
||||
content_type: concept
|
||||
-->
|
||||
<!-- overview -->
|
||||
|
||||
<!-- body -->
|
||||
<!--
|
||||
## Node-level troubleshooting {#troubleshooting-node}
|
||||
|
||||
1. My Pods are stuck at "Container Creating" or restarting over and over
|
||||
|
||||
Ensure that your pause image is compatible with your Windows OS version.
|
||||
See [Pause container](/docs/setup/production-environment/windows/intro-windows-in-kubernetes#pause-container)
|
||||
to see the latest / recommended pause image and/or get more information.
|
||||
|
||||
{{< note >}}
|
||||
If using containerd as your container runtime the pause image is specified in the
|
||||
`plugins.plugins.cri.sandbox_image` field of the of config.toml configration file.
|
||||
{{< /note >}}
|
||||
-->
|
||||
## 工作节点级别排障 {#troubleshooting-node}
|
||||
|
||||
1. 我的 Pod 都卡在 “Container Creating” 或者不断重启
|
||||
|
||||
确保你的 pause 镜像跟你的 Windows 版本兼容。
|
||||
查看 [Pause 容器](zh/docs/setup/production-environment/windows/intro-windows-in-kubernetes#pause-container)
|
||||
以了解最新的或建议的 pause 镜像,或者了解更多信息。
|
||||
|
||||
{{< note >}}
|
||||
如果你使用了 containerd 作为你的容器运行时,pause 镜像在 config.toml 配置文件的
|
||||
`plugins.plugins.cri.sandbox_image` 中指定。
|
||||
{{< /note >}}
|
||||
<!--
|
||||
2. My pods show status as `ErrImgPull` or `ImagePullBackOff`
|
||||
|
||||
Ensure that your Pod is getting scheduled to a [compatable](https://docs.microsoft.com/virtualization/windowscontainers/deploy-containers/version-compatibility) Windows Node.
|
||||
|
||||
More information on how to specify a compatable node for your Pod can be found in [this guide](docs/setup/production-environment/windows/user-guide-windows-containers/#ensuring-os-specific-workloads-land-on-the-appropriate-container-host).
|
||||
-->
|
||||
2. 我的 pod 状态显示 'ErrImgPull' 或者 ‘ImagePullBackOff’
|
||||
|
||||
保证你的 Pod 被调度到[兼容的](https://docs.microsoft.com/virtualization/windowscontainers/deploy-containers/version-compatibility) Windows 节点上。
|
||||
|
||||
关于如何为你的 Pod 指定一个兼容节点,
|
||||
的更多信息可以查看这个指可以查看[这个指南](/zhdocs/setup/production-environment/windows/user-guide-windows-containers/#ensuring-os-specific-workloads-land-on-the-appropriate-container-host)以了解更多的信息。
|
||||
<!--
|
||||
## Network troubleshooting {#troubleshooting-network}
|
||||
|
||||
1. My Windows Pods do not have network connectivity
|
||||
|
||||
If you are using virtual machines, ensure that MAC spoofing is **enabled** on all
|
||||
the VM network adapter(s).
|
||||
-->
|
||||
## 网络排障 {#troubleshooting-network}
|
||||
|
||||
1. 我的 Windows Pod 没有网络连接
|
||||
|
||||
如果你使用的是虚拟机,请确保所有 VM 网卡上都已启用 MAC spoofing。
|
||||
<!--
|
||||
2. My Windows Pods cannot ping external resources
|
||||
|
||||
Windows Pods do not have outbound rules programmed for the ICMP protocol. However,
|
||||
TCP/UDP is supported. When trying to demonstrate connectivity to resources
|
||||
outside of the cluster, substitute `ping <IP>` with corresponding
|
||||
`curl <IP>` commands.
|
||||
|
||||
If you are still facing problems, most likely your network configuration in
|
||||
[cni.conf](https://github.com/Microsoft/SDN/blob/master/Kubernetes/flannel/l2bridge/cni/config/cni.conf)
|
||||
deserves some extra attention. You can always edit this static file. The
|
||||
configuration update will apply to any new Kubernetes resources.
|
||||
|
||||
One of the Kubernetes networking requirements
|
||||
(see [Kubernetes model](/docs/concepts/cluster-administration/networking/)) is
|
||||
for cluster communication to occur without
|
||||
NAT internally. To honor this requirement, there is an
|
||||
[ExceptionList](https://github.com/Microsoft/SDN/blob/master/Kubernetes/flannel/l2bridge/cni/config/cni.conf#L20)
|
||||
for all the communication where you do not want outbound NAT to occur. However,
|
||||
this also means that you need to exclude the external IP you are trying to query
|
||||
from the `ExceptionList`. Only then will the traffic originating from your Windows
|
||||
pods be SNAT'ed correctly to receive a response from the outside world. In this
|
||||
regard, your `ExceptionList` in `cni.conf` should look as follows:
|
||||
|
||||
```conf
|
||||
"ExceptionList": [
|
||||
"10.244.0.0/16", # Cluster subnet
|
||||
"10.96.0.0/12", # Service subnet
|
||||
"10.127.130.0/24" # Management (host) subnet
|
||||
]
|
||||
```
|
||||
-->
|
||||
2. 我的 Windows Pod 不能 ping 通外界资源
|
||||
|
||||
Windows Pod 没有为 ICMP 协议编写出站规则,但 TCP/UDP 是支持的。当试图演示与集群外部资源的连接时,可以把 `ping <IP>` 替换为 `curl <IP>` 命令。
|
||||
|
||||
如果你仍然遇到问题,很可能你需要额外关注
|
||||
[cni.conf](https://github.com/Microsoft/SDN/blob/master/Kubernetes/flannel/l2bridge/cni/config/cni.conf)
|
||||
的配置。你可以随时编辑这个静态文件。更新配置将应用于新的 Kubernetes 资源。
|
||||
|
||||
Kubernetes 的网络需求之一 (查看 [Kubernetes 模型](/zh/docs/concepts/cluster-administration/networking/))
|
||||
是集群通信不需要内部的 NAT。
|
||||
为了遵守这一要求, 对于你不希望发生的出站 NAT 通信,这里有一个
|
||||
[ExceptionList](https://github.com/Microsoft/SDN/blob/master/Kubernetes/flannel/l2bridge/cni/config/cni.conf#L20) 。
|
||||
然而,这也意味着你需要从 `ExceptionList` 中去掉你试图查询的外部IP。
|
||||
只有这样,来自你的 Windows Pod 的流量才会被正确地 SNAT 转换,以接收来自外部环境的响应。
|
||||
就此而言,你的 `cni.conf` 中的 `ExceptionList` 应该如下所示:
|
||||
|
||||
```conf
|
||||
"ExceptionList": [
|
||||
"10.244.0.0/16", # Cluster subnet
|
||||
"10.96.0.0/12", # Service subnet
|
||||
"10.127.130.0/24" # Management (host) subnet
|
||||
]
|
||||
```
|
||||
<!--
|
||||
3. My Windows node cannot access `NodePort` type Services
|
||||
|
||||
Local NodePort access from the node itself fails. This is a known
|
||||
limitation. NodePort access works from other nodes or external clients.
|
||||
|
||||
4. vNICs and HNS endpoints of containers are being deleted
|
||||
|
||||
This issue can be caused when the `hostname-override` parameter is not passed to
|
||||
[kube-proxy](/docs/reference/command-line-tools-reference/kube-proxy/). To resolve
|
||||
it, users need to pass the hostname to kube-proxy as follows:
|
||||
|
||||
```powershell
|
||||
C:\k\kube-proxy.exe --hostname-override=$(hostname)
|
||||
```
|
||||
-->
|
||||
3. 我的 Windows 节点无法访问 `NodePort` 类型服务
|
||||
|
||||
从节点本身访问本地 NodePort 失败,是一个已知的限制。你可以从其他节点或外部客户端正常访问 NodePort。
|
||||
|
||||
4. 容器的 vnic 和 HNS endpoints 正在被删除
|
||||
|
||||
当 `hostname-override` 参数没有传递给 [kube-proxy](/zh/docs/reference/command-line-tools-reference/kube-proxy/)
|
||||
时可能引发这一问题。想要解决这个问题,用户需要将主机名传递给 kube-proxy,如下所示:
|
||||
|
||||
```powershell
|
||||
C:\k\kube-proxy.exe --hostname-override=$(hostname)
|
||||
```
|
||||
<!--
|
||||
5. My Windows node cannot access my services using the service IP
|
||||
|
||||
This is a known limitation of the networking stack on Windows. However, Windows Pods can access the Service IP.
|
||||
|
||||
6. No network adapter is found when starting the kubelet
|
||||
|
||||
The Windows networking stack needs a virtual adapter for Kubernetes networking to work.
|
||||
If the following commands return no results (in an admin shell),
|
||||
virtual network creation — a necessary prerequisite for the kubelet to work — has failed:
|
||||
|
||||
```powershell
|
||||
Get-HnsNetwork | ? Name -ieq "cbr0"
|
||||
Get-NetAdapter | ? Name -Like "vEthernet (Ethernet*"
|
||||
```
|
||||
|
||||
Often it is worthwhile to modify the [InterfaceName](https://github.com/microsoft/SDN/blob/master/Kubernetes/flannel/start.ps1#L7) parameter of the start.ps1 script,
|
||||
in cases where the host's network adapter isn't "Ethernet".
|
||||
Otherwise, consult the output of the `start-kubelet.ps1` script to see if there are errors during virtual network creation.
|
||||
-->
|
||||
5. 我的 Windows 节点无法通过服务 IP 访问我的服务
|
||||
|
||||
这是 Windows 上网络栈的一个已知限制。但是 Windows Pod 可以访问 Service IP。
|
||||
|
||||
6. 启动 kubelet 时找不到网络适配器
|
||||
|
||||
Windows 网络栈需要一个虚拟适配器才能使 Kubernetes 网络工作。
|
||||
如果以下命令没有返回结果(在管理员模式的 shell 中),
|
||||
则意味着创建虚拟网络失败,而虚拟网络的存在是 kubelet 正常工作前提:
|
||||
|
||||
```powershell
|
||||
Get-HnsNetwork | ? Name -ieq "cbr0"
|
||||
Get-NetAdapter | ? Name -Like "vEthernet (Ethernet*"
|
||||
```
|
||||
|
||||
如果主机的网络适配器不是 "Ethernet",通常有必要修改 `start.ps1` 脚本的
|
||||
[InterfaceName](https://github.com/microsoft/SDN/blob/master/Kubernetes/flannel/start.ps1#L7) 参数。
|
||||
否则,如果虚拟网络创建过程出错,请检查 `start-kubelet.ps1` 脚本的输出。
|
||||
<!--
|
||||
7. DNS resolution is not properly working
|
||||
|
||||
Check the DNS limitations for Windows in this [section](#dns-limitations).
|
||||
|
||||
8. `kubectl port-forward` fails with "unable to do port forwarding: wincat not found"
|
||||
|
||||
This was implemented in Kubernetes 1.15 by including `wincat.exe` in the pause infrastructure container `mcr.microsoft.com/oss/kubernetes/pause:3.6`.
|
||||
Be sure to use a supported version of Kubernetes.
|
||||
If you would like to build your own pause infrastructure container be sure to include [wincat](https://github.com/kubernetes/kubernetes/tree/master/build/pause/windows/wincat).
|
||||
-->
|
||||
7. DNS 解析工作异常
|
||||
|
||||
在[本节](#dns-limitations)中了解 Windows 系统上的 DNS 限制。
|
||||
|
||||
8. `kubectl port-forward` 失败,错误为 "unable to do port forwarding: wincat not found"
|
||||
|
||||
在 Kubernetes 1.15 中,pause 基础架构容器 `mcr.microsoft.com/oss/kubernetes/pause:3.6`
|
||||
中包含 `wincat.exe` 来实现端口转发。
|
||||
请确保使用 Kubernetes 的受支持版本。如果你想构建自己的 pause 基础架构容器,
|
||||
请确保其中包含 [wincat](https://github.com/kubernetes/kubernetes/tree/master/build/pause/windows/wincat)。
|
||||
<!--
|
||||
9. My Kubernetes installation is failing because my Windows Server node is behind a proxy
|
||||
|
||||
If you are behind a proxy, the following PowerShell environment variables must be defined:
|
||||
|
||||
```PowerShell
|
||||
[Environment]::SetEnvironmentVariable("HTTP_PROXY", "http://proxy.example.com:80/", [EnvironmentVariableTarget]::Machine)
|
||||
[Environment]::SetEnvironmentVariable("HTTPS_PROXY", "http://proxy.example.com:443/", [EnvironmentVariableTarget]::Machine)
|
||||
```
|
||||
-->
|
||||
9. 我的 Kubernetes 安装失败,因为我的 Windows 服务器节点使用了代理服务器
|
||||
|
||||
如果使用了代理服务器,必须定义下面的 PowerShell 环境变量:
|
||||
|
||||
```PowerShell
|
||||
[Environment]::SetEnvironmentVariable("HTTP_PROXY", "http://proxy.example.com:80/", [EnvironmentVariableTarget]::Machine)
|
||||
[Environment]::SetEnvironmentVariable("HTTPS_PROXY", "http://proxy.example.com:443/", [EnvironmentVariableTarget]::Machine)
|
||||
```
|
||||
<!--
|
||||
### Flannel troubleshooting
|
||||
|
||||
1. With Flannel, my nodes are having issues after rejoining a cluster
|
||||
|
||||
Whenever a previously deleted node is being re-joined to the cluster, flannelD
|
||||
tries to assign a new pod subnet to the node. Users should remove the old pod
|
||||
subnet configuration files in the following paths:
|
||||
|
||||
```powershell
|
||||
Remove-Item C:\k\SourceVip.json
|
||||
Remove-Item C:\k\SourceVipRequest.json
|
||||
```
|
||||
-->
|
||||
## Flannel 故障排查 {#troubleshooting-network}
|
||||
|
||||
1. 使用 Flannel 时,我的节点在重新加入集群后出现问题
|
||||
|
||||
当先前删除的节点重新加入集群时, flannelD 尝试为节点分配一个新的 Pod 子网。
|
||||
用户应该在以下路径中删除旧的 Pod 子网配置文件:
|
||||
|
||||
```powershell
|
||||
Remove-Item C:\k\SourceVip.json
|
||||
Remove-Item C:\k\SourceVipRequest.json
|
||||
```
|
||||
<!--
|
||||
2. Flanneld is stuck in "Waiting for the Network to be created"
|
||||
|
||||
There are numerous reports of this [issue](https://github.com/coreos/flannel/issues/1066);
|
||||
most likely it is a timing issue for when the management IP of the flannel network is set.
|
||||
A workaround is to relaunch `start.ps1` or relaunch it manually as follows:
|
||||
|
||||
```powershell
|
||||
[Environment]::SetEnvironmentVariable("NODE_NAME", "<Windows_Worker_Hostname>")
|
||||
C:\flannel\flanneld.exe --kubeconfig-file=c:\k\config --iface=<Windows_Worker_Node_IP> --ip-masq=1 --kube-subnet-mgr=1
|
||||
```
|
||||
-->
|
||||
2. Flanneld 卡在 "Waiting for the Network to be created"
|
||||
|
||||
关于这个[问题](https://github.com/coreos/flannel/issues/1066)有很多报告 ;
|
||||
很可能是 flannel 网络管理 IP 的设置时机问题。
|
||||
一个变通方法是重新启动 `start.ps1` 或按如下方式手动重启:
|
||||
|
||||
```powershell
|
||||
[Environment]::SetEnvironmentVariable("NODE_NAME", "<Windows 工作节点主机名>")
|
||||
C:\flannel\flanneld.exe --kubeconfig-file=c:\k\config --iface=<Windows 工作节点 IP> --ip-masq=1 --kube-subnet-mgr=1
|
||||
```
|
||||
<!--
|
||||
3. My Windows Pods cannot launch because of missing `/run/flannel/subnet.env`
|
||||
|
||||
This indicates that Flannel didn't launch correctly. You can either try
|
||||
to restart `flanneld.exe` or you can copy the files over manually from
|
||||
`/run/flannel/subnet.env` on the Kubernetes master to `C:\run\flannel\subnet.env`
|
||||
on the Windows worker node and modify the `FLANNEL_SUBNET` row to a different
|
||||
number. For example, if node subnet 10.244.4.1/24 is desired:
|
||||
|
||||
```env
|
||||
FLANNEL_NETWORK=10.244.0.0/16
|
||||
FLANNEL_SUBNET=10.244.4.1/24
|
||||
FLANNEL_MTU=1500
|
||||
FLANNEL_IPMASQ=true
|
||||
```
|
||||
-->
|
||||
3. 我的 Windows Pod 无法启动,因为缺少 `/run/flannel/subnet.env`
|
||||
|
||||
这表明 Flannel 没有正确启动。你可以尝试重启`flanneld.exe` 或者你可以将 Kubernetes 控制节点的
|
||||
`/run/flannel/subnet.env` 文件手动拷贝到 Windows 工作节点上,放在 `C:\run\flannel\subnet.env`;
|
||||
并且将 `FLANNEL_SUBNET` 行修改为不同取值。例如,如果期望节点子网为 10.244.4.1/24:
|
||||
|
||||
```env
|
||||
FLANNEL_NETWORK=10.244.0.0/16
|
||||
FLANNEL_SUBNET=10.244.4.1/24
|
||||
FLANNEL_MTU=1500
|
||||
FLANNEL_IPMASQ=true
|
||||
```
|
||||
<!--
|
||||
### Further investigation
|
||||
|
||||
If these steps don't resolve your problem, you can get help running Windows containers on Windows nodes in Kubernetes through:
|
||||
|
||||
* StackOverflow [Windows Server Container](https://stackoverflow.com/questions/tagged/windows-server-container) topic
|
||||
* Kubernetes Official Forum [discuss.kubernetes.io](https://discuss.kubernetes.io/)
|
||||
* Kubernetes Slack [#SIG-Windows Channel](https://kubernetes.slack.com/messages/sig-windows)
|
||||
-->
|
||||
### 进一步探查 {#further-investigation}
|
||||
|
||||
如果这些步骤都不能解决你的问题,你可以通过以下方式获得关于在 Kubernetes 中运行 Windows 容器的帮助:
|
||||
|
||||
* StackOverflow [Windows Server Container](https://stackoverflow.com/questions/tagged/windows-server-container) topic
|
||||
* Kubernetes 官方论坛 [discuss.kubernetes.io](https://discuss.kubernetes.io/)
|
||||
* Kubernetes Slack [#SIG-Windows Channel](https://kubernetes.slack.com/messages/sig-windows)
|
||||
Reference in New Issue
Block a user