Kubernetes 与 Traefik 101 — 简单至上

2025-06-05

Kubernetes 与 Traefik 101 — 简单至上

这个教程可以让我免去几个小时与键盘搏斗的时间

您是否曾经遇到过这样的情况:...

工作中的某人: “看,这非常简单,让我解释一下......”

…继续……

[……充满神秘术语的痛苦……]

同一位热情的同事: “你看,你明白了吗?”

你(面无表情): “当然,明白了,啊哈,没问题,哇,确实超级简单,啊哈……”

……但最终你还是偷偷溜进浴室,胡言乱语地说出一堆你几乎不记得的关键词。

“Ok Google,节点立方体中的 Ingress 集群是什么?……请帮帮我。”

没有。我从来没遇到过这种情况。一次也没有。没有,先生!

但是,让我们假设这件事在几年前确实发生过(假设),并且我在研究过程中偶然发现的所有文章都是由如此神秘的符号组成的,以至于我开始流泪(而且不是喜悦的泪水)。

我说:我们假装一下吧。

因此,基于这个虚构的情况,让我们尝试编写一个最简单的教程,介绍如何将 Traefik 设置为 Kubernetes 的 Ingress Controller。(我保证:我会解释所有不太明显的部分。)

如果您熟悉 Kubernetes,可以跳过此部分。

关于 Kubernetes,你需要知道什么

Kubernetes,即 Cluster

Kubernetes 是一种集群技术。这意味着您将把一组计算机视为一个整体。您无需将应用程序部署到特定的计算机上,而是部署到集群中的某个位置,Kubernetes 的工作就是确定最符合您应用程序需求的计算机。

集群中的机器可以具有不同的特性

节点

集群中的每台计算机称为一个节点。最终,这些节点将托管您的应用程序。这些节点可以分布在世界各地的不同数据中心,而 Kubernetes 的职责就是让它们像邻居一样进行通信。

节点是集群中的机器

容器

我想你已经熟悉容器了。如果你不熟悉,我来解释一下:它们曾经是虚拟化的下一步,而如今,它们已经成为了虚拟化的事实标准。你无需配置一台机器来托管你的应用程序,而是将应用程序(以及应用程序所需的一切——操作系统、库、依赖项……)包装到容器中,并部署到托管容器引擎的机器上,而容器引擎负责实际运行容器。

从技术上讲,容器并不属于 Kubernetes;它们只是交易工具之一。

容器嵌入所需的技术

基本上,Kubernetes 看到的容器如下图所示:

容器引擎负责处理容器所需的底层技术

豆荚

由于 Kubernetes 偏爱分层,因此 Kubernetes 在容器周围添加了 Pod 的概念。Pod 是最终部署到集群的最小单元。一个 Pod 可以容纳多个容器,但为了简单起见,我们暂时假设一个 Pod 只托管一个容器。

因此,在 Kubernetes 的世界里,Pod 是你的应用程序实例、服务实例的新名称。Pod 将托管在节点上,而 Kubernetes 的工作是确定哪个节点托管哪个 Pod。

如果一个 Pod 由多个容器组成,它们将共享相同的资源/网络

部署

有趣的部分来了!部署是你向 Kubernetes 提出的关于你的应用程序(你的 Pod)的要求。基本上,通过部署,你可以告诉 Kubernetes:

嘿,Kube,始终保持这些 Pod 的 5 个实例(或副本)处于运行状态 — 始终如此。

Kubernetes 的工作是确保您的集群在任何给定时间托管 Pod 的 5 个副本。

Kubernetes 负责将 Pod 部署到正确的位置

服务

哦,又一个有趣的概念……

Pod 的生命周期是不稳定的;它们按照 Kubernetes 的意愿来来去去。

不健康?杀了。

不在正确的地方?克隆,然后杀死。

(不,你绝对不想被 Kube 统治!)

那么,如果你不能确定应用程序位于何处,该如何向它发送请求呢?答案在于服务。

服务定义了已部署的 Pod 集,因此您可以向“应用程序类型的任何可用 Pod”发送请求。

当请求你的应用程序时,你不必关心它的位置或哪个 pod 响应请求

入口

所以我们的集群中有 Pod。

我们拥有服务,因此我们可以在集群内部与它们通信。(从技术上讲,有一些方法可以从外部提供服务,但我们暂时先略过这部分。)

现在,我们希望将我们的服务推向互联网,以便客户可以访问我们的产品。

入口对象是定义应该存在的路由的规则。

Ingress 对象是定义我们服务路由的规则

入口控制器

现在您已经定义了从外部访问服务的规则,您所需要的只是一个根据规则路由传入请求的组件......这些组件称为入口控制器!

由于这是本文的主题——Traefik 是 Kubernetes 的一个出色的 Ingress 控制器。

关于 Traefik 你需要知道什么

  • 太棒了。
  • 它很容易使用。
  • 它已准备好投入生产并被大公司使用。
  • 它适用于现有的所有主要集群技术。
  • 它是开源的
  • 它非常受欢迎;撰写本文时下载量已超过 1.5 亿次。

……哦?我的观点有偏见吗?嗯,也许吧……但以上都是真的!

让我们开始把所有东西整合在一起!

这是我们实际开始将服务部署到 Kube 集群并将 Traefik 配置为 Ingress Controller 的部分。

先决条件

您可以访问 Kubernetes 集群,并且拥有指向该集群的kubectl 。

你知道,这里我使用的是嵌入在 Docker for Mac中的 Kubernetes 。

我们将做什么

  • 我们将使用一个预制容器——containous/whoami——它可以告诉你它的托管位置以及调用时会收到什么。(很抱歉让你失望了,但我可以确认我们不会在这里构建新的杀手级应用^^)
  • 我们将定义两个不同的 Pod,一个whoami和一个whoareyou,它们将使用此容器。
  • 我们将创建一个部署,要求 Kubernetes 部署 1 个whoami副本和 2 个whoareyou副本(因为我们更关心他人而不是自己……多么体贴!)。
  • 我们将定义两个服务,每个 Pod 一个。
  • 我们将定义 Ingress 对象来定义到我们服务的路由。
  • 我们将把 Traefik 设置为我们的 Ingress 控制器。

因为我们喜欢图表,所以图片如下:

使用 Helm 设置 Traefik

Helm是 Kube 的包管理器,对我来说,它是配置 Traefik 最便捷的方式,而且不会弄乱它。(如果您还没有安装 Helm,安装起来非常简单,只需两行命令即可,例如brew install kubernetes-helmhelm init。)

要设置 Traefik,请复制/粘贴以下命令行:

helm install stable/traefik --set dashboard.enabled=true,dashboard.domain=dashboard.localhost
Enter fullscreen mode Exit fullscreen mode

在上面的命令行中,我们启用了仪表板(dashboard.enabled=true)并使其在http://dashboard.localhostdashboard.domain=localhost.domain)上可用。

helm install 命令行的输出将如下所示:

就我而言,EXTERNAL-IP已经可用并且是localhost

EXTERNAL-IP是我的集群的门的地址;它是 Ingress Controller(Traefik)的公共地址。

正如我们之前所说,我们应该能够立即访问仪表板!

仪表板显示 Traefik 已检测到一项服务(右侧称为 dashboard.localhost)并已创建到该服务的路由(左侧称为 host:dashboard.localhost)

让我们部署一些 Pod!

现在是时候部署我们的第一个 WhoAmI!

提醒一下,我们需要一个带有一个容器的 Pod(containous/whoami)。

相当简单的 Pod

Kubernetes 使用 yaml 文件来描述其对象,因此我们将使用一个文件来描述我们的部署。

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: whoami-deployment
spec:
replicas: 1
selector:
matchLabels:
app: whoami
template:
metadata:
labels:
app: whoami
spec:
containers:
- name: whoami-container
image: containous/whoami
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: whoami-deployment
spec:
replicas: 1
selector:
matchLabels:
app: whoami
template:
metadata:
labels:
app: whoami
spec:
containers:
- name: whoami-container
image: containous/whoami

对文件内容进行一些解释:

  • 我们定义一个“部署”(kind: Deployment
  • 该对象的名称是“whoami-deployment”(name: whoami-deployment
  • 我们想要一个副本(replicas: 1
  • 它将部署带有标签 app:whoami 的 pod(选择器:matchLabels: app:whoami
  • 然后我们定义 pod(模板:...
  • Pod 将具有 whoami 标签(metadata:labels:app:whoami
  • Pod 将使用镜像 containous/whoami ( image:containous/whoami )托管一个容器

📗 注意:您可以在 Kubernetes 文档中阅读有关部署的更多信息。

现在我们已经描述了我们的部署,我们要求 Kubernetes 使用以下命令考虑该文件:

kubectl apply -f whoami-deployment.yml
Enter fullscreen mode Exit fullscreen mode

让我们检查一下发生了什么:

kubectl get all
Enter fullscreen mode Exit fullscreen mode

whoami-deployment 已创建

让我们定义一项服务!

如果您没有记错的话,我们需要服务,以便我们可以与特定类型的“任何可用的 Pod”进行对话。

我们需要 whoami 服务来引用我们的 whoami pod

再次,我们需要定义对象:

apiVersion: v1
kind: Service
metadata:
name: whoami-service
spec:
ports:
- name: http
targetPort: 80
port: 80
selector:
app: whoami
apiVersion: v1
kind: Service
metadata:
name: whoami-service
spec:
ports:
- name: http
targetPort: 80
port: 80
selector:
app: whoami

一些解释:

  • 我们定义一个“服务”(kind: Service
  • 该对象的名称是“whoami-service”(name: whoami-service
  • 它将监听端口 80 并重定向到端口 80(端口:...
  • 目标 Pod 具有标签 whoami ( selector:app:whoami )

📗 注意:您可以在 Kubernetes 文档中阅读有关服务的更多信息。

现在我们已经描述了我们的服务,我们要求 Kubernetes 使用以下命令考虑该文件:

kubectl apply -f whoami-service.yml
Enter fullscreen mode Exit fullscreen mode

让我们检查一下发生了什么:

kubectl get all
Enter fullscreen mode Exit fullscreen mode

我们的服务随时可用!

入口

最后,我们即将制定规则,以便全世界都能从我们的(超棒)服务中受益。

您知道该怎么做,让我们编写 YML 文件来描述新对象:

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: whoami-ingress
annotations:
kubernetes.io/ingress.class: traefik
spec:
rules:
- host: whoami.localhost
http:
paths:
- path: /
backend:
serviceName: whoami-service
servicePort: http
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: whoami-ingress
annotations:
kubernetes.io/ingress.class: traefik
spec:
rules:
- host: whoami.localhost
http:
paths:
- path: /
backend:
serviceName: whoami-service
servicePort: http

一些解释:

  • 我们定义一个“入口”(kind: Ingress
  • 该对象的名称是“whoami-ingress”(name: whoami-ingress
  • Ingress 的类名为“traefik”(kubernetes.io/ingress.class:traefik)。这个类很重要,因为它告诉 Traefik 需要考虑这个 Ingress。
  • 我们为这个 Ingress 添加规则(规则:...)
  • 我们希望将对主机 whoami.localhost (host:whoami.localhost) 的请求通过 http (servicePort: http) 重定向到服务 whoami-service (serviceName:whoami-service)。

📗 注意:您可以在 Kubernetes 文档中阅读有关 Ingress 的更多信息。

现在我们已经描述了我们的 Ingress,我们要求 Kubernetes 使用以下(相同的旧)命令来考虑该文件:

kubectl apply -f whoami-ingress.yml
Enter fullscreen mode Exit fullscreen mode

现在,由于 Traefik 是我们的 Ingress 控制器,让我们看看仪表板中是否有变化……

Traefik 已自动检测到新的 Ingress!

就是这样,无需重新加载,也无需添加额外的配置文件(配置文件已经够多了)。Traefik 已更新其配置,现在可以处理 whoami.localhost 路由了!

让我们检查一下……

Traefik 按预期重定向请求

是的,我们的服务很有用,但它的用户界面还需要一些改进❤️

在这里,我们确认 Traefik我们的 Ingress 控制器,并且它已准备好将其功能引入您的服务!

我可以询问实际的负载平衡吗?

之前,我们讨论了具有 2 个副本的 WhoAreYou 部署。

让我们只在一个文件中完成它:-)

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: whoareyou-deployment
spec:
replicas: 2
selector:
matchLabels:
app: whoareyou
template:
metadata:
labels:
app: whoareyou
spec:
containers:
- name: whoareyou-container
image: containous/whoami
---
apiVersion: v1
kind: Service
metadata:
name: whoareyou-service
spec:
ports:
- name: http
targetPort: 80
port: 80
selector:
app: whoareyou
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: whoareyou-ingress
annotations:
kubernetes.io/ingress.class: traefik
spec:
rules:
- host: whoareyou.localhost
http:
paths:
- path: /
backend:
serviceName: whoareyou-service
servicePort: http
view raw whoareyou.yml hosted with ❤ by GitHub
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: whoareyou-deployment
spec:
replicas: 2
selector:
matchLabels:
app: whoareyou
template:
metadata:
labels:
app: whoareyou
spec:
containers:
- name: whoareyou-container
image: containous/whoami
---
apiVersion: v1
kind: Service
metadata:
name: whoareyou-service
spec:
ports:
- name: http
targetPort: 80
port: 80
selector:
app: whoareyou
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: whoareyou-ingress
annotations:
kubernetes.io/ingress.class: traefik
spec:
rules:
- host: whoareyou.localhost
http:
paths:
- path: /
backend:
serviceName: whoareyou-service
servicePort: http
view raw whoareyou.yml hosted with ❤ by GitHub

这里没什么好说的,只是这次我们有 2 个副本……(副本:2)

因此,让我们要求 Kubernetes 应用我们的新配置文件。

kubectl apply -f whoareyou.yml
Enter fullscreen mode Exit fullscreen mode

让我们立即进入 Traefik 的仪表板。

瞧!

Traefik 检测到新的 Ingress 和服务中的两个可用 Pod

第一个请求,其中一个 Pod 回复

第二个请求,另一个 Pod 回复

结论

如果我想写一篇文章来介绍如何“仅仅”将 Traefik 配置为 Kubernetes 的 Ingress Controller,那么一行就可以写完:

helm install stable/traefik
Enter fullscreen mode Exit fullscreen mode

因为这实际上是我们在本文中唯一需要的配置操作。其余的只是解释和演示。

是的,这一步确实就是这么简单!

与 Traefik 一起走得更远!

现在您已经知道如何配置 Traefik,现在可能是深入研究其文档并了解其其他功能(自动 HTTPS、Let's Encrypt 自动支持、断路器、负载平衡、重试、websocket、HTTP2、GRPC、指标等)的好时机。

Containous是一家帮助 Træfik 成为成功的开源项目的公司(并为 Traefik 提供商业支持)。

在 Twitter 上关注Træfik :-)

欢迎您发表评论和提问!

您可以从我的 github 存储库geraldcroes/kubernetes-traefik-article克隆文件

文章来源:https://dev.to/geraldcroes/kubernetes--traefik-101-when-simplicity-matters-6k6
PREV
免费 Web 开发资源
NEXT
为什么编码标准很重要?