traefik 作为一款稳定的网关,一直被很多微服务使用,目前traefik升级到了 2 版本,增加了针对tcp的支持,因为更新时间不长,还没有针对新版的中文文档,新版的文档在 官网,如果使用之前的版本,可以参考中文文档,之前在搭建k8s集群时曾经尝试过使用traefik 1+ 的版本,后来因为项目时间问题,最后放弃了使用k8s,也就没有仔细去体会traefik的强大功能。最近因为另一个项目有一些需求,计划使用traefik来做API网关,才翻出来看看,结果发现更新到了2.0版本,竟然支持TCP了,好了,废话不多说,开始体验一下新版的功能吧!

为了方便学习并去除系统差异,我将直接使用Docker来做环境,traefik 中支持 docker 模式,并能支持docker原生的swarm模式,下面我将统一使用docker-compose来做说明

首先我们先创建一个简单的例子,使用官方提供的 containous/whoami 来作为应用镜像,其可以显示请求的具体信息,以便一会做请求时来确认具体访问到的是哪个容器

下面我们来创建一个 docker-compose.yml 编排文件

version: "3.4"
services:
    traefik:
        image: traefik:v2.1
        ports:
            - "80:80"
            - "8080:8080"
        volumes: 
            - "/var/run/docker.sock:/var/run/docker.sock"
        command: 
            - "--api.insecure=true"
            - "--api.dashboard=true"
            - "--accesslog=true"
            - "--providers.docker=true"
            - "--entrypoints.web.address=:80"
    whoami:
        image: containous/whoami
        labels: 
            - "traefik.http.routers.app.rule=Host(`localhost`)"
            - "traefik.http.routers.app.entrypoints=web"

上面这个编排文件中,我们开放traefik与docker的守护进程通信

volumes: 
    - "/var/run/docker.sock:/var/run/docker.sock"

在启动命令中,我们首先开启了 dashboard 为了本地调试,我们使用 insecure 来开启不安全接口访问方便我们做本地调试

- "--api.insecure=true"
- "--api.dashboard=true"

开启日志,方便我们调试

- "--accesslog=true"

目前 traefik 支持多种工作方式,具体文档可以见官方文档

我们指明目前工作模式为docker方式

- "--providers.docker=true"

我们新建一个名为web的入口并让其监听80端口

- "--entrypoints.web.address=:80"

现在我们已经配置完了traefik,我们再配置一个containous/whoami的应用来演示traefik的功能

traefik使用labels来配置应用的路由、中间件等,目前我将仅配置路由,让这个简单的事例可以运行起来

首先我们来配置一个名为app的路由,traefik其将会把域名为localhost的请求负载均衡的分配给这个应用的每个容器中

- "traefik.http.routers.app.rule=Host(`localhost`)"

现在我们再配置这个应用的入口为我们刚才定义的名为web的入口

- "traefik.http.routers.app.entrypoints=web"

现在,编排文件写完了,我们来运行docker-compose,为了方便看到日志,我们没有使用 -d 来后台运行,并且我们将启动3个应用来方便我们查看负载均衡的情况

docker-compose -f docker-compose.yml up --scale whoami=3 

等镜像都拉取完成后,我们看到启动成功了

现在我们用浏览器访问下 localhost 并多刷新几次,观察下变化

我们的多次访问被分别分配到来不同的容器中,从日志中我们也能看到,访问被调度到了 172.18.0.2 172.18.0.5 172.18.0.3 三个不同的容器中

现在我们再来访问 localhost:8080 可以看到非常炫酷的新版仪表盘

新版仪表盘

从上到下我们可以看到当前定义了 808080 两个入口,启用了4个路由,4个服务和2个中间件,开启了访问日志,并使用了Docker Providers

下面我来分别对每个页面做下说明,首先我们点到HTTP页面

routers

此页面列出了当前启用的4个路由,第一个是路径前缀,点进去我们可以看到如下图

path prefix api router

其将8080入口的请求,符合规则以路径/api为开头的请求,分发到api@internal这个服务中去,这个是一个traefik的内部路由,其就是我们仪表盘操作的api接口

我们再回到刚才的页面,看第二个路由定义,这个就是我们在whoami中用labels定义的规则,我们点进去看到如下图

app router

我们可以看到其规则为 符合Hostlocalhost,名称为app@docker,这里的app是我们在刚才的docker-compose中通过labels定义的名,而后面的@docker是因为我们在docker中定义的所以是这样的名,如果我们通过traefik的配置文件来定义,则其名称将为app@file,我们还以看到,其是将80端口的请求,通过这个路由,分配给whoami-treafik2这个服务

再回到列表页,第三个路由则是是一个traefik中仪表盘相关的路由,点进去看下

use middleware

这个路由将8080端口的请求,经过路由后,使用了两个中间件,再转发给仪表盘服务,我们着重看下这两个中间件

其中一个名为dashboard_stripprefix@internal的中间件,其是将请求的前缀移除掉,这里配置的是移除掉 /dashboard/ /dashboard 前缀,这样请求到后端容器中,其就去掉了请求的这些前缀,官方文档在这里 stripprefix

另一个名为dashboard_redirect@internal的中间件,其则会将符合正则的内容替换掉,这里是将 /的请求跳转到 /dashboard/ 下,所以我们在访问 http://localhost:8080/ 的请求才会被跳转到 http://localhost:8080/dashboard/ 下,官方文档在这里 redirectregex

下面我们再来到services的列表,如下图

我就不一个个说明了,我们只看下我们定义的whoami-treafik2@docker这个服务,点进去看如下图

我们可以看到,其采用了loadbalancer负载,并且由三个服务的容器IP

再进到中间件列表,如下图

这里我们看到我们刚才说明的两个中间件都在这里,我就不再进去一一说明了

总之,初次探索traefik,我们通过一个简单的docker-compose编排文件,轻易的搭建了一个拥有三个节点负载均衡的集群,今天就到这里,下一篇文章我将开始一步步完善这个小集群,开始加入https以及一些更多的中间件

本篇文章相关的代码在这里 https://github.com/jarod2011/traefik2-tutorials/blob/master/lesson_1/

traefik的相关文章可以见这里