本文已超过一年。较旧的文章可能包含过时内容。请检查页面中的信息自发布以来是否已失效。

为人所理解地注解 Kubernetes Service

您是否曾被要求排除 Kubernetes 服务故障,却难以找到有关该服务的基本信息,例如源代码仓库和所有者?

随着 Kubernetes 应用的增长,服务数量激增成为问题之一。随着服务数量增加,开发者开始专注于处理特定服务。然而,在故障排除时,开发者需要能够找到源代码、理解服务及其依赖关系,并与任何服务的所有者团队沟通。

人工服务发现

故障排除总是从信息收集开始。虽然人们对集中式机器数据(例如日志、指标)投入了大量关注,但对服务发现的人工方面关注较少。谁拥有特定的服务?团队在哪个 Slack 频道工作?服务的源代码在哪里?当前有哪些已知问题正在跟踪?

Kubernetes 注解 (Annotations)

Kubernetes 注解正是为了解决这个问题而设计的。Kubernetes 注解经常被忽视,它们用于向 Kubernetes 对象添加元数据。Kubernetes 文档指出,注解可以“向对象附加任意的非标识性元数据”。这意味着注解应用于附加与 Kubernetes 外部相关的元数据(即 Kubernetes 不会用于标识对象的元数据)。因此,注解可以包含任何类型的数据。这与用于 Kubernetes 内部用途的标签不同。因此,标签的结构和值受到 限制,以便 Kubernetes 可以高效地使用它们。

Kubernetes 注解的实践应用

下面是一个示例。假设您有一个用于报价的 Kubernetes 服务,称为 quote 服务。您可以执行以下操作:

kubectl annotate service quote a8r.io/owner=”@sally”

在此示例中,我们添加了一个名为 a8r.io/owner 的注解,其值为 @sally。现在,我们可以使用 kubectl describe 命令获取信息。

Name:              quote
Namespace:         default
Labels:            <none>
Annotations:       a8r.io/owner: @sally
Selector:          app=quote
Type:              ClusterIP
IP:                10.109.142.131
Port:              http  80/TCP
TargetPort:        8080/TCP
Endpoints:         <none>
Session Affinity:  None
Events:            <none>

如果您正在实践 GitOps(并且您应该如此!),您会希望将这些值直接编码到您的 Kubernetes 清单文件中,例如:

apiVersion: v1
kind: Service
metadata:
  name: quote
  annotations:
    a8r.io/owner: “@sally”
spec:
  ports:
  - name: http
    port: 80
    targetPort: 8080
  selector:
    app: quote

注解约定

采用通用的注解约定可确保一致性和可理解性。通常,您会希望将注解附加到 Service 对象上,因为 Service 是最高级别的资源,最清晰地对应到团队的职责。为您的注解添加命名空间也非常重要。以下是在 a8r.io 记录并在此处转载的一组约定:

人工可读服务的注解约定
注解 (Annotation)描述 (Description)
a8r.io/description供人工阅读的服务非结构化文本描述。
a8r.io/ownerSSO 用户名 (GitHub)、邮箱地址 (关联到 GitHub 账户),或非结构化的所有者描述。
a8r.io/chatSlack 频道,或外部聊天系统的链接。
a8r.io/bugs外部 bug 跟踪器的链接。
a8r.io/logs外部日志查看器的链接。
a8r.io/documentation外部项目文档的链接。
a8r.io/repository外部版本控制系统 (VCS) 仓库的链接。
a8r.io/support外部支持中心的链接。
a8r.io/runbook外部项目运行手册的链接。
a8r.io/incidents外部事件仪表板的链接。
a8r.io/uptime外部正常运行时间仪表板的链接。
a8r.io/performance外部性能仪表板的链接。
a8r.io/dependencies供人工阅读的服务依赖关系非结构化文本描述。

注解可视化:服务目录

随着微服务和注解数量的激增,运行 kubectl describe 可能会变得繁琐。此外,使用 kubectl describe 要求每个开发者都能直接访问 Kubernetes 集群。在过去几年中,服务目录在 Kubernetes 生态系统中获得了更高的关注度。由 Shopify 的 ServicesDB 和 Spotify 的 System Z 等工具推广开来,服务目录是面向内部的开发者门户,用于展示有关微服务的关键信息。

请注意,这些服务目录不应与 Kubernetes Service Catalog 项目混淆。Kubernetes Service Catalog 构建在 Open Service Broker API 之上,它使 Kubernetes 操作员能够将不同的服务(例如数据库)插入到其集群中。

现在就为您的服务添加注解,将来您会感谢自己

就像在微服务系统中实现可观测性一样,您通常直到为时已晚(例如生产环境发生故障)才意识到您需要人工服务发现。不要等到生产环境出现问题时才开始希望您已经实现了更好的指标,并记录了如何联系负责该服务的部分组织人员。

构建有效的“版本 0”服务有巨大的好处:一个“跳舞的骨架”应用,它包含一小部分完整的功能,可以通过最小但有效的持续交付管道部署到生产环境。

为您的所有服务添加服务注解应成为您的“版本 0”的关键部分。现在就添加它们,将来您会感谢自己。