首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >警告:有用的警告|让Kubernetes的使用越来越容易

警告:有用的警告|让Kubernetes的使用越来越容易

作者头像
CNCF
发布2020-09-14 15:02:10
1.8K0
发布2020-09-14 15:02:10
举报
文章被收录于专栏:CNCFCNCF

作者:Jordan Liggitt(谷歌)

作为Kubernetes的维护者,我们一直在寻找在保持兼容性的同时提高可用性的方法。在开发特性、分类bug和回答支持问题的过程中,我们积累了有助于Kubernetes用户了解的信息。在过去,信息的共享仅限于发布说明、公告电子邮件、文档和博客文章等外部方法。除非有人知道该信息并设法找到它,否则他们不会从中受益。

在Kubernetes v1.19中,我们添加了一个特性,允许Kubernetes API服务器向API客户机发送警告。警告是使用标准的Warning响应头发送的,因此它不会以任何方式更改状态代码或响应体。这允许服务器发送警告,任何API客户端都可以轻松读取,同时保持与以前的客户端版本兼容。

警告在kubectl v1.19+的stderr输出和k8s.io/client-go客户端库v0.19.0+的日志输出。k8s.io/client-go的设定可以按进程或按客户端覆盖。

弃用的警告

我们使用这个新功能的第一种方式是,对使用已弃用的API(deprecated API)发送警告。

Kubernetes是一个快速发展的大型项目。即使对于全职从事项目的人来说,跟上每个版本中的变化也是一件令人生畏的事情。一种重要的改变是API的弃用。随着Kubernetes中的API升级到GA版本,预发布的API版本将被弃用并最终被删除。

即使有一个延长的弃用期,并且在发布说明中包含了弃用,它们仍然很难跟踪。在弃用期间,预发布API仍然有效,允许多个版本转换为稳定的API版本。然而,我们发现,用户通常甚至没有意识到他们所依赖的API版本已经弃用,直到他们升级到不再提供它的版本。

从v1.19开始,每当向弃用的REST API发出请求时,都会在API响应的同时返回一个警告。此警告包括有关API将不再可用的版本的详细信息,以及替换的API版本。

因为警告来自服务器,在客户端被拦截,所以它适用于所有的kubectl命令,包括像kubectl apply这样的高级命令,和像kubectl get --raw这样的低级命令:

这有助于受弃用影响的人知道他们发出的请求已被弃用,他们需要多长时间来解决这个问题,以及他们应该使用什么API来替代。当用户应用自己没有创建的清单时,这尤其有用,这样他们就有时间联系作者,要求更新版本。

我们还意识到,使用已弃用API的人通常不是负责升级集群的同一个人,因此我们添加了两个面向管理员的工具,以帮助跟踪已弃用API的使用情况,并确定何时升级是安全的。

指标

从Kubernetes v1.19开始,当向已弃用的REST API端点发出请求时,在kube-apiserver进程中将apiserver_requested_deprecated_apis度量指标设置为1。此指标具有API group、version、resource、subresource的标签,以及一个removed_version标签,该标签指示不再提供API的Kubernetes版本。

这是一个使用kubectl、prom2json和jq的示例查询,用于确定API服务器的当前实例请求了哪些弃用的API:

kubectl get --raw /metrics | prom2json | jq '
  .[] | select(.name=="apiserver_requested_deprecated_apis").metrics[].labels
'

输出:

{
  "group": "extensions",
  "removed_release": "1.22",
  "resource": "ingresses",
  "subresource": "",
  "version": "v1beta1"
}
{
  "group": "rbac.authorization.k8s.io",
  "removed_release": "1.22",
  "resource": "clusterroles",
  "subresource": "",
  "version": "v1beta1"
}

这显示了弃用的extensions/v1beta1 Ingress和rbac.authorization.k8s.io/v1beta1 ClusterRole API在此服务器上被请求,将在v1.22中被删除。

我们可以将这些信息与apiserver_request_total指标连接起来,以获得关于向这些API发出的请求的更多细节:

kubectl get --raw /metrics | prom2json | jq '
  # set $deprecated to a list of deprecated APIs
  [
    .[] | 
    select(.name=="apiserver_requested_deprecated_apis").metrics[].labels |
    {group,version,resource}
  ] as $deprecated 
  
  |
  
  # select apiserver_request_total metrics which are deprecated
  .[] | select(.name=="apiserver_request_total").metrics[] |
  select(.labels | {group,version,resource} as $key | $deprecated | index($key))
'

输出:

{
  "labels": {
    "code": "0",
    "component": "apiserver",
    "contentType": "application/vnd.kubernetes.protobuf;stream=watch",
    "dry_run": "",
    "group": "extensions",
    "resource": "ingresses",
    "scope": "cluster",
    "subresource": "",
    "verb": "WATCH",
    "version": "v1beta1"
  },
  "value": "21"
}
{
  "labels": {
    "code": "200",
    "component": "apiserver",
    "contentType": "application/vnd.kubernetes.protobuf",
    "dry_run": "",
    "group": "extensions",
    "resource": "ingresses",
    "scope": "cluster",
    "subresource": "",
    "verb": "LIST",
    "version": "v1beta1"
  },
  "value": "1"
}
{
  "labels": {
    "code": "200",
    "component": "apiserver",
    "contentType": "application/json",
    "dry_run": "",
    "group": "rbac.authorization.k8s.io",
    "resource": "clusterroles",
    "scope": "cluster",
    "subresource": "",
    "verb": "LIST",
    "version": "v1beta1"
  },
  "value": "1"
}

输出显示,只对这些API发出读请求,大多数请求是为了监视已弃用的Ingress API。

你还可以通过以下Prometheus查询找到该信息,该查询返回关于对将在v1.22中删除的已弃用API的请求的信息:

apiserver_requested_deprecated_apis{removed_version="1.22"} * on(group,version,resource,subresource)
group_right() apiserver_request_total

审计注释

指标是检查是否正在使用弃用API,以及使用速度的一种快速方法,但是它们没有包含足够的信息来识别特定的客户机或API对象。从Kubernetes v1.19开始,对已弃用API的请求的审计事件包括一个审计注释"k8s.io/deprecated":"true"。管理员可以使用这些审计事件来标识需要更新的特定客户端或对象。

Custom Resource Definitions

从v1.19开始,除了API服务器警告已弃用API的功能外,CustomResourceDefinition还可以指示它所定义的资源的特定版本已被弃用。当API请求自定义资源的已弃用版本时,将返回一条警告消息,与内置API的行为相匹配。

如果需要,CustomResourceDefinition的作者还可以为每个版本定制警告。这允许他们提供一个指向迁移指南的指针,或者在需要时提供其他信息。

apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
  name: crontabs.example.com
spec:
  versions:
  - name: v1alpha1
    # This indicates the v1alpha1 version of the custom resource is deprecated.
    # API requests to this version receive a warning in the server response.
    deprecated: true
    # This overrides the default warning returned to clients making v1alpha1 API requests.
    deprecationWarning: "example.com/v1alpha1 CronTab is deprecated; use example.com/v1 CronTab (see http://example.com/v1alpha1-v1)"
    ...


  - name: v1beta1
    # This indicates the v1beta1 version of the custom resource is deprecated.
    # API requests to this version receive a warning in the server response.
    # A default warning message is returned for this version.
    deprecated: true
    ...


  - name: v1
    ...

Admission Webhooks

Admission webhook是与Kubernetes集成自定义策略或验证的主要方式。从v1.19开始,admission webhook可以返回警告消息,这些消息被传递到请求API客户端。警告可以与允许或拒绝录取回答一起返回。

例如,允许一个请求,但警告一个已知的配置不工作,admission webhook可以发送这样的响应:

{
  "apiVersion": "admission.k8s.io/v1",
  "kind": "AdmissionReview",
  "response": {
    "uid": "<value from request.uid>",
    "allowed": true,
    "warnings": [
      ".spec.memory: requests >1GB do not work on Fridays"
    ]
  }
}

如果你正在实现一个webhook返回一个警告消息,这里有一些提示:

  • 不要在消息中包含“Warning:”前缀(这是客户端在输出中添加的)
  • 使用警告消息来描述发出API请求的客户端应该纠正或注意的问题
  • 精简;如果可能,将警告限制在120个字符

admission webhook使用这个新特性的方式有很多,我很期待看到人们会提出什么。这里有一些建议让你开始:

  • webhook实现增加了一个“complain”模式,在这里他们返回警告而不是拒绝,以允许尝试一个策略,以验证它是否正常工作,然后开始实施它
  • “lint”或“vet”风格的webhook,检查对象和没有遵循最佳实践是提供警告

Kubectl严格模式

如果你想确保尽快注意到弃用并立即着手解决它们,kubectl在v1.19中添加了一个--warnings-as-errors选项。使用此选项调用时,kubectl将从服务器接收到的任何警告视为错误,并以非零退出代码退出:

这可以在CI作业中用于将清单应用到当前服务器,并且需要使用零退出代码传递,以表示CI作业成功。

未来的可能性

现在,我们已经有了一种方法,可以在上下文中向用户传递有用的信息,我们在考虑使用这种方法来改善用户使用Kubernetes的体验。我们讨论了的两个方面是关于已知有问题的值的警告,由于兼容性原因,我们不能完全拒绝这些值,以及关于使用不推荐使用的字段或字段值的警告(比如使用beta os/arch节点标签的selector,在v1.14弃用)。我很高兴看到这一领域的进展,Kubernetes的使用越来越容易。

Jordan Liggitt是谷歌的一名软件工程师,帮助领导Kubernetes的认证、授权和API工作。

本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2020-09-08,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 CNCF 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
容器服务
腾讯云容器服务(Tencent Kubernetes Engine, TKE)基于原生 kubernetes 提供以容器为核心的、高度可扩展的高性能容器管理服务,覆盖 Serverless、边缘计算、分布式云等多种业务部署场景,业内首创单个集群兼容多种计算节点的容器资源管理模式。同时产品作为云原生 Finops 领先布道者,主导开源项目Crane,全面助力客户实现资源优化、成本控制。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档