Step by Step!教你如何在k3s集群上使用Traefik 2.x

本文来自边缘计算k3s社区

作者简介

Cello Spring,瑞士人。从电子起步,拥有电子工程学位。尔后开始关注计算机领域,在软件开发领域拥有多年的工作经验。

Traefik是一个十分可靠的云原生动态反向代理。轻量级Kubernetes发行版K3s早在去年就已经内置Traefik,将其作为集群的默认反向代理和Ingress Controller。然而,在本文成文时K3s中的默认内置Traefik版本为v1.7.14。这一版本固然也能很好地运行,但还是少了一些有用的功能。我最想用的功能是为正在使用的Ingress Route自动生成Let’s Encrypt证书。而使用Traefik 2.x版本可以获得这一功能,甚至还有更多其他功能。那么,我们来看看如何使用K3s设置并使用新版本的Traefik。

本文的目标是设置一个新的K3s集群、安装Traefik 2.x版本并配置一些Ingress,这些Ingress将由自动生成的Let’s Encrypt证书保护。

以下是我们将要进行的步骤:

  • 在Civo上创建一个极小的K3s集群

  • 将我们的域(我会使用我的虚拟域celleri.ch)指向集群IP

  • 安装Klipper LB作为我们的LoadBalancer

  • 在集群上安装Traefik v2

  • 部署一个小型工作负载(whoami)到集群上

  • 创建一个Traefik ingress到服务(分为有TLS termination或没有)

  • 使用Traefik 中间件以通过基本身份验证访问Traefik Dashboard

创建Civo集群

为此,请到Civo(civo.com/)并创建一个只有2个节点的超小型集群。如果你还没有账户,可以注册并申请KUBE100 Beta项目以使用其提供的Kubernetes产品。

需要确保我们不使用基本设置安装Traefik(在“Architecture”选项卡上取消选择Traefik)

大约2分钟之后,我们将获得以下集群:

在这里插入图片描述

接下来,我们需要记下master节点的IP地址并下载kubeconfig文件。在本例中,它被命名为civo-k3s-with-traefik2-kubeconfig,因为我们将集群命名为k3s-with-traefik2。为了使用kubectl从命令行中访问该集群,我们需要将环境变量指向kubeconfig文件并将上下文更改至我们的新集群。

# set env variable with new cluster config
export KUBECONFIG=./civo-k3s-with-traefik2-kubeconfig
kubectl config use-context k3s-with-traefik2

#check the available nodes
kubectl get nodes

NAME               STATUS   ROLES    AGE     VERSION
kube-master-de56   Ready    master   9m15s   v1.16.3-k3s.2
kube-node-40e7     Ready       7m21s   v1.16.3-k3s.2

正如我们所见,带有1个master节点和1个worker节点的集群已经准备完毕!继续进行下一步。

将域名Celleri.ch指向新的集群IP地址

最近一段时间,我一直使用Cloudflare(cloudflare.com/dns/)的DNS服务来处理Kubernetes。它十分可靠,有友好的用户界面并且我使用的基本服务都是免费的。

在Cloudflare中我们应用以下设置:

本示例中,我们不想为可能用到的每个子域都创建一个CNAME条目,因此我们在此处创建一个通配符(*)条目作为CNAME。Traefik将确保稍后将流量路由到正确的位置。

安装Klipper LB作为我们的LoadBalancer

默认情况下,K3s内置的Traefik为v1.7.x版本。默认安装还部署了来自Rancher的内部LoadBalancer,Klipper LB。由于在设置集群时,我们没有安装Traefik,因此我们现在必须自己手动安装Klipper LB。

Klipper会将自己挂接到集群节点的主机端口上,并使用端口80、443和8080。

你可以在我的Github Repo里找到我所提到的所有文件:

https://github.com/cellerich/k3s-with-traefik2

# install KlipperLB
kubectl apply -f 00-klipper-lb/klipper.yaml

# see if klipper hooked up to the host ports and is working
kc get pods --all-namespaces | grep svclb
kube-system  svclb-traefik-gc8lg     3/3     Running   0          96s
kube-system  svclb-traefik-pqbzb     3/3     Running   0          96s

这些Pod似乎可以与在其中运行的3个容器(每个主机端口一个容器)一起工作。接下来,我们开始安装Traefik v2。

在集群中安装Traefik v2

Traefik v2附带了许多CRD,这似乎是扩展Kubernetes对象的一种新方法。我还没有完全把精力放在这些CRD上面,但是无论如何我们都要使用它们。你可以在Traefik文档(https://docs.traefik.io/v2.0/user-guides/crd-acme/)中找到正确的yaml文件,或者你可以使用我在Github repo上提供的01-traefik-crd/traefik-crd.yaml文件。

# apply traefik crd's
kubectl apply -f 01-traefik-crd/traefik-crd.yaml

这个命令应该会创建5个CRD。

为了让Traefik可以做它所需要做的事情,我们需要一个clusterrole和一个clusterrolebinding。我们可以使用以下命令:

# apply clusterrole and clusterrolebinding
kubectl apply -f 01-traefik-crd/traefik-clusterrole.yaml

请注意:我们将在命名空间kube-system中为ServiceAccount进行clusterrolebinding,因为稍后我们会将流量安装到该命名空间中。


kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  name: traefik-ingress-controller

roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: traefik-ingress-controller
subjects:
  - kind: ServiceAccount
    name: traefik-ingress-controller
    namespace: kube-system

最后,我们把Traefik Service、ServiceAccount以及Deployment部署到集群中:

kubectl apply -f 02-traefik-service/traefik.yaml

这应该为我们提供一个LoadBalancer类型的服务,该服务具有集群的master节点的外部地址:

# get traefik service
kubectl get svc -n kube-system | grep traefik

traefik          LoadBalancer   192.168.211.177   185.136.232.122   80:32286/TCP,443:30108/TCP,8080:30582/TCP   3m43s

部署一个小型工作负载(whoami)到集群

现在是时候在我们的集群中创建一个服务并尝试通过我们的Traefik代理从外部调用它。本示例中我使用的是whoami服务,它也用于Traefik文档中的所有示例。让我们部署它:


# deploy `whoami` in namespace `default`
kubectl apply -f 03-workload/whoami-service.yaml

#check the deployment 
kubectl get pods | grep whoami

whoami-bd6b677dc-lfxbx   1/1     Running   0          5m37s
whoami-bd6b677dc-92jzj   1/1     Running   0          5m37s

好像已经可以运行了。现在要到激动人心的部分了,Traefik Ingress。

为服务创建两个Traefik Ingress(有/没有TLS Termination)

我们想要从外部访问whoami服务,以让我们最终可以定义IngressRoute对象。没错,那些对象是在我们之前安装的CRD中定义的。现在它们派上用场了。我们按照以下方式部署IngressRoutes:

kubectl apply -f 03-workload/whoami-ingress-route.yaml

正如你在定义中所看到的,我们使用tls.certResolver=default指定了一个路由(附带PathPrefix '/tls')。该certResolver在我们的02-traefik-service / traefik.yaml文件中定义。


apiVersion: traefik.containo.us/v1alpha1
kind: IngressRoute
metadata:
  name: ingressroute-notls
  namespace: default
spec:
  entryPoints:
    - web
  routes:
    - match: Host(`celleri.ch`) && PathPrefix(`/notls`)
      kind: Rule
      services:
        - name: whoami
          port: 80

---
apiVersion: traefik.containo.us/v1alpha1
kind: IngressRoute
metadata:
  name: ingressroute-tls
  namespace: default
spec:
  entryPoints:
    - websecure
  routes:
    - match: Host(`celleri.ch`) && PathPrefix(`/tls`)
      kind: Rule
      services:
        - name: whoami
          port: 80
  tls:
    certResolver: default

现在启动浏览器并访问地址http://celleri.ch/notls,查看即将发生的事情——pod正在响应:

在这里插入图片描述

那么https://celleri.ch/tls发生了什么呢?它也在正常运行,但是告诉我们第一个连接不安全。如果我们查看证书,我们就能找到原因:

在这里插入图片描述

为了防止因我们的安装程序无法正常工作而使生产服务器受到许多请求的困扰,我们一开始没有使用Let’s Encrypt,而在Traefik Service中使用staging服务器。因此,我们接下来要更改这一设置并使用生产服务器获得一个真实的证书。

更改certresolver以使用Let’s Encrypt生产服务器

在我们定义的Traefik Deployment中,我们有以下参数:


 ... cropped for readability ...

    spec:
      serviceAccountName: traefik-ingress-controller
      containers:
        - name: traefik
          image: traefik:v2.0
          args:
            - --api.insecure
            - --accesslog
            - --entrypoints.web.Address=:80
            - --entrypoints.websecure.Address=:443
            - --providers.kubernetescrd
            - --certificatesresolvers.default.acme.tlschallenge
            - --certificatesresolvers.default.acme.email=me@myself.com
            - --certificatesresolvers.default.acme.storage=acme.json
            # Please note that this is the staging Let's Encrypt server.
            - --certificatesresolvers.default.acme.caserver=https://acme-staging-v02.api.letsencrypt.org/directory

    ... cropped for readability ...

我们告诉Traefik使用tlschallenge的方法来使用名为default的certificateresolvers。此外,我们还需要提供我们的邮件和证书的存储。我们在前文中还提到我们要使用staging caserver。

重点:在我们的部署中,我们没有存储提供程序或者volume。这意味着,部署重新加载后我们的证书就会消失。证书仅存在于我们的pod内存中。在生产环境中,我们必须解决这一问题并提供一个volume。

好的,让我们注释掉caserver行,然后重新部署Traefik deployment,看看我们是否获得了真实的证书:


  ... cropped for readability ...

    spec:
      serviceAccountName: traefik-ingress-controller
      containers:
        - name: traefik
          image: traefik:v2.0
          args:
            - --api.insecure
            - --accesslog
            - --entrypoints.web.Address=:80
            - --entrypoints.websecure.Address=:443
            - --providers.kubernetescrd
            - --certificatesresolvers.default.acme.tlschallenge
            - --certificatesresolvers.default.acme.email=me@myself.com
            - --certificatesresolvers.default.acme.storage=acme.json
            # Please note that this is the staging Let's Encrypt server.
            # - --certificatesresolvers.default.acme.caserver=https://acme-staging-v02.api.letsencrypt.org/directory

    ... cropped for readability ...
# deploy the changed file
kubectl apply -f 02-traefik-service/traefik.yaml

一会儿之后,我们将获得一个有效证书:

在这里插入图片描述

在这之后,我们可以稍稍放轻松了。但是我们想更近一步,Traefik v2还有一个不错的dashboard,可以查看正在运行的所有Ingress内容。但是我们并不希望每个人都能访问我们的dashboard。有一些基本的身份验证可以更好地保护我们的dashboard。

使用Traefik 中间件以通过基本身份验证访问Traefik Dashboard

在Traefik 2.x中引入了一个新机制——中间件,该机制在处理传入请求时可以帮助我们完成许多任务。我们将使用basicAuth中间件来保护Traefik dashboard并将其暴露给外部。

首先,我们需要使用我们的用户名和哈希密码创建一个Secret,以便basicAuth 中间件在以后使用:

# create user:password file 'user'
htpasswd -c ./user cellerich

# enter password twice...

# create secret from password file 
kubectl create secret generic traefik-admin --from-file user -n kube-system

确保在命名空间kube-system内创建该Secret,因为Traefik Service及其Dashboard也位于此命名空间中。

然后我们部署该中间件以及IngressRoute到我们的集群:

kubectl apply -f 04-traefik-dashboard/traefik-admin-withauth.yaml

现在,我们访问https://traefik.celleri.ch,出现登陆提示:

在这里插入图片描述

使用正确的凭据,我们将访问Traefik v2的dashboard:

在这里插入图片描述

并且我们会获得许多关于我们Ingress Route的信息:

在这里插入图片描述

结 语

这就是教程的全部。在研究过程中,我没有发现太多关于如何在k3s中设置Traefik v2的示例,特别是Klipper LB的部分从未被提及。这就是为什么我想向大家分享我的经验,希望它能够帮助到你,退一万步来说,至少它对我的将来会有所帮助。

参考链接:

Github :

https://github.com/cellerich/k3s-with-traefik2

关于Rancher的Klipper LB:

https://github.com/rancher/klipper-lb

Traefik中间件文档:

https://docs.traefik.io/v2.0/middlewares/overview/

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 205,033评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 87,725评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,473评论 0 338
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,846评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,848评论 5 368
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,691评论 1 282
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,053评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,700评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 42,856评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,676评论 2 323
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,787评论 1 333
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,430评论 4 321
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,034评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,990评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,218评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,174评论 2 352
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,526评论 2 343

推荐阅读更多精彩内容

  • 注:本文使用的Traefik为1.x的版本 在生产环境中,我们常常需要控制来自互联网的外部进入集群中,而这恰巧是I...
    RancherLabs阅读 1,298评论 0 3
  • 原文链接:一文搞懂 Traefik2.1 的使用 Traefik 是一个开源的可以使服务发布变得轻松有趣的边缘路由...
    k8s技术圈阅读 4,395评论 0 5
  • 不曾做过评批, 面对贫瘠的书架。 我想, 就像风匿茵丛, 你是我的眉骨间。
    五维天空阅读 119评论 0 1
  • 生活里总是遇到各种奇葩委屈。 比如科室里少了两盒礼品,怀疑是我俩轮转生拿的,其实我们之前就已经在护理部拿过了。 比...
    廿小阙阅读 177评论 0 0
  • 网上购买的小苗到了,购买指南里第一名“老园丁”家4棵,月季花跳蚤市场吧“秦川牛”家2棵。指南还是非常实在的,收到的...
    爪先生阅读 277评论 0 1