提升效能:Kubernetes环境下的必备工具与实践

227 阅读7分钟

写作目的

在前公司(sangfor)的工作主要是负责云原生架构以及效能相关的提升,一直想编写一篇文章来将自己kubernetes环境下的开发工具以及技巧总结一下。

如果你使用的是kubernetes环境, 并且对这个玩意儿的上手成本,理解比较困难,这是一篇能够启发到的文章。

开发工具

大多服务都是采用微服务,通过服务间通信(HTTP,RPC)等进行相互调用,完成业务逻辑。 在kubernetes演进过程中,第一个遇到的问题:网络。

k8s通过CNI实现了内部集群网络,在k8s集群外部无法直接调用到使用ClusterIp的服务,更加无法访问pod id的方式调用服务。那开发怎么办,有以下几种方式:

  1. 通过编译,出包上传镜像的方式,进行功能调试, 这也是大多数开发第一反应,最简单,最耗时妥协的方式。然后脑子产生疑问:为啥上了k8s效能降低了?
  2. 将k8s集群内部的svc修改成nodeport的方式,在缺乏工具的情况下,可以使用这种方式访问集群内部服务,在本地机器上完成调试。这个解决了访问集群内部上游服务的问题:

画板

画板

注:最好不直接修改部署好的svc,而是通过**kuberctl expose**重新创建一个新的。

  1. 通过telepresence拦截集群内部相同服务流量,实现在本地开发,调试的效果;

这个解决了单人调试单个服务的环境问题。 那么在多个人使用同一套环境,同时进行开发的情况,我们该如何处理了?

  1. 流量染色开发模式,在大厂或者效能比较完善的公司,通过自研或者二开相关工具,达成一个共享一套环境的目的:

画板

画板

这种情况下,使用telepresence肯定是不行了,所以如果是小公司的话,有两种可以直接使用的方案:okteto+istio , nocalhost。

nocalhost:我使用的时候,grpc/HTTP2不太能支持。

个人推荐okteto+istio,okteto能够轻量的直接替换k8s内部的pod, istio可以自定义流量的转发。**这两者合并将达成流量染色的方案。 **

如果更加精进的话,可以将okteto进行二次开发,将它的配置Yaml文件,直接执行流量染色的配置。(之前已经实现,后续有空开源出来)。

排查工具

网络问题排查:

在 Kubernetes 环境中,确保服务间正确调用是一个常见的挑战。以下是一些优化后的方法,可以帮助开发人员确认他们的服务是否成功调用了上游服务:

  1. 检查服务端点

    • 验证 Kubernetes 服务(Service)关联的端点(Endpoints)列表是否包含预期的 Pod IP 地址。
  2. 域名解析测试

    • 使用 nslookup 命令检查服务名称的 DNS 解析是否迅速且正确,确保没有解析延迟或错误。
  3. 检查网络配置

    • 确认容器网络接口(CNI)组件是否正常工作,这关系到 Pod 之间的网络连通性。
  4. 利用 Istio 的日志

    • 如果你的集群中部署了 Istio 服务网格,可以查看 Istio Sidecar 代理的日志。这些日志提供了流量的详细信息,可以帮助你追踪请求是否到达了预期的服务。
  5. 检查服务发现机制

    • 确保服务发现机制(如 DNS 或环境变量)正确配置,并且服务间能够相互发现。
  6. 网络策略

    • 检查网络策略是否允许服务间的通信,确保没有安全规则阻止了合法的流量。
  7. 健康检查

    • 实施和依赖 Kubernetes 的 Liveness 和 Readiness 探针,以确保服务健康并且准备好接收流量。

通过这些步骤,开发人员可以更有信心地确定他们的服务是否能够正确地与上游服务进行通信。

服务排查优化

  1. 使用 k9s 替代 kubectl

    • 利用 k9s 提供的图形界面,通过 tmux 或 screen 分屏查看 Kubernetes 服务状态,简化服务管理操作。
  2. 服务状态监控

    • 通过 k9s 监控服务的实时状态,包括部署、状态检查和事件日志。
  3. 资源配置管理

    • 使用版本控制系统(如 Git)管理 Kubernetes 资源配置的 YAML 文件,简化资源部署和回滚。
  4. 自动化脚本

    • 编写脚本自动化常规的 kubectl 查询和操作,减少重复性工作。

链路排查优化

  1. 分布式追踪系统

    • 采用 OpenTelemetry + Jaeger 组合进行分布式链路追踪,快速定位问题服务。
  2. 链路追踪数据优化

    • 合理配置链路追踪,避免记录敏感信息,减少存储压力。
  3. 性能监控

    • 结合 Prometheus 和 Grafana 监控服务性能,及时发现性能瓶颈。

日志管理优化

  1. 集中式日志系统

    • 使用 ELK Stack(Elasticsearch, Logstash, Kibana)或 Loki 进行日志收集和分析。
  2. 日志索引策略

    • 将 TraceId 作为日志的索引字段,便于追踪和查询相关日志。
  3. 日志级别管理

    • 根据需要调整日志级别,避免产生过多无用日志。
  4. 日志分析工具

    • 利用日志分析工具(如 EFK 或 Loki Canary)进行智能日志分析。

部署工具

部署工具优化

配置管理策略

  • 初始阶段,采用第三方配置中心(如 Nacos)来实现配置与程序二进制的分离管理。

面临的挑战

在发布过程中,频繁的配置变更导致效率低下,尤其是当线上网络策略限制时,需要通过跳板机修改配置,这严重影响了服务升级的效率。

优化方案:将配置文件与应用程序打包,形成一个发布包,简化部署流程。

工具选择:采用 ConfigMap 管理配置文件,并结合 Golang 的 Viper 库实现动态配置监听和修改。

版本控制:使用 Git 来管理 Helm chart 的 values.yaml 文件,实现配置的版本归档。

环境配置管理:为每个环境维护一个特定的 values 文件(如 values-<环境>.yaml),并在 Helm 升级时与默认的 values.yaml 合并生效。

部署流程:利用 Helm 进行应用的打包和部署,确保每次升级只需发布新的版本包。

编码思考

  1. 项目结构优化

    • 采用 Kratos 项目结构,这是一种经过验证的微服务框架,有助于保持代码的组织性和可扩展性。
  2. 架构选择

    • 利用领域驱动设计(DDD)的六边形架构,确保了业务逻辑与基础设施之间的清晰分离。
  3. 单元测试

    • 每一层都可以独立进行单元测试,这是确保代码质量的关键步骤。
  4. 测试驱动开发(TDD)

    • 在编码过程中,如果遇到难以单元测试的功能,采用测试驱动开发的方法,先编写测试用例再实现功能。
  5. 设计模式学习

    • 深入学习设计模式,这有助于解决常见的软件设计问题,并提高代码的灵活性和可重用性。
  6. 代码重构

    • 定期进行代码重构,以消除技术债务,提高代码质量。

总结时刻

自动化是提高效率的关键,它让我们能够减少重复劳动并专注于更有价值的事情

面对挑战,我们应该主动寻找解决方案,而不是被动应对。通过不断改进工作方式,我们可以提升自己的技能,实现个人成长。(持续学习)

记住,不是工作内容本身,而是我们不断提升的工作方法,才是成长的驱动力。


另外:不要太在乎绩效/评价,这些都是主观性非常强的,过于关注只会内耗自己,认真的做好自己的事非常重要,对一件事尽力是种能力。不要觉得这件事没做好是自己没认真,逃避失败的借口罢了。

PS:遇到傻逼的上司,自认倒霉准备跑路即可。