详讲api网关之kong的基本概念及安装和使用(二)
consul的服务注册与发现
如果不知道consul的使用,可以点击上方链接,这是我写的关于consul的一篇文档。
upstream+consul实现负载均衡
我们知道,配置upstream可以实现负载均衡,而consul实现了服务注册与发现,那么接下来我们就来看看利用这两个组件怎么实现负载均衡吧。
安装consul
- docker安装consul,注意端口,注意将consul的网络加入到kong的网络中,即
--network=kong-ee-net
docker run -d --name consul \--network=kong-ee-net \-p 8500:8500 \-p 8300:8309 \-p 8301:8301 \-p8302:8302 \-p 8600:8600/udp \hashicorp/consul consul agent -dev -client=0.0.0.0
gin服务注册到consul
- 我们启动3个gin服务,并注册到consul中,相关代码如下,注意,服务端口是随机获取的,并注册到consul中,我们几乎不需要关心端口是多少
package main
import ("fmt""gin-demo/config""gin-demo/db""gin-demo/route""gin-demo/utils""github.com/fvbock/endless"consulapi "github.com/hashicorp/consul/api"
)
// 定义服务注册的信息
type ServiceConfig struct {ID stringName stringTags []stringPort intAddress string
}// consul的服务地址
var consulIp = "127.0.0.1:8500"// 注册
func RegisterSevice(s ServiceConfig) error {consulConfig := consulapi.DefaultConfig()consulConfig.Address = consulIp//获取到客户端client, err := consulapi.NewClient(consulConfig)if err != nil {fmt.Printf("create consul client : %v\n", err.Error())return err}registration := &consulapi.AgentServiceRegistration{ID: s.ID,Name: s.Name,Port: s.Port,Tags: s.Tags,Address: s.Address,}if err := client.Agent().ServiceRegister(registration); err != nil {fmt.Printf("register to consul error: %v\n", err.Error())return err}return nil
}func main() {//配置文件config.InitConfig()//sql初始化db.NewDb().InitAllSql()//启动r := route.InitRoute()//随机获取一个可用端口_, port := utils.RandomPort()//注册到consulconsulPort := fmt.Sprintf("%d", port)service := ServiceConfig{ID: consulPort,Name: "blog_service",Tags: []string{"blog"},Port: port,Address: "192.168.11.20",}err := RegisterSevice(service)if err != nil {fmt.Printf("register to consul error: %v\n", err.Error())}//启动gin服务addr := fmt.Sprintf(":%d", port)err = endless.ListenAndServe(addr, r)if err != nil {return}
}
-
启动完毕之后,我们访问consul的web页面已注册成功
http://127.0.0.1:8500/ui/dc1/services/blog_service/instances
-
我们使用dns的方式访问一下
dig @127.0.0.1 -p 8600 blog_service.service.consul
kong里面配置consul
- 通过
docker network inspect kong-ee-net
查看consul的ip为172.23.0.4 - 这里我们需要删除原来的kong容器,并使用以下命令创建一个新看kong,需要注意的是,由于你指定了KONG_DNS_RESOLVER,那么原来指定的KONG_PG_HOST就不可以再用dns的方式,因为consul里面并没有这个域名,会导致服务启动报错。所以要直接指定ip。
docker run -d --name kong \--network=kong-ee-net \-e "KONG_DATABASE=postgres" \-e "KONG_DNS_RESOLVER=192.168.11.20:8600" \-e "KONG_PG_HOST=172.23.0.2" \-e "KONG_PG_USER=kong" \-e "KONG_PG_PASSWORD=kong" \-e "KONG_CASSANDRA_CONTACT_POINTS=kong-database" \-e "KONG_PROXY_ACCESS_LOG=/dev/stdout" \-e "KONG_ADMIN_ACCESS_LOG=/dev/stdout" \-e "KONG_PROXY_ERROR_LOG=/dev/stderr" \-e "KONG_ADMIN_ERROR_LOG=/dev/stderr" \-e "KONG_ADMIN_LISTEN=0.0.0.0:8001, 0.0.0.0:8444 ssl" \-p 8000:8000 \-p 8443:8443 \-p 8001:8001 \-p 8444:8444 \kong-oss:latest
-
启动之后,我们会再konga里面看到下面这行,这个时候,我们在kong里面配置的域名都会被 consul解析
-
我们配置
blog_service.service.consul
给service,就是咱们原来创建的blog的service
-
我们现在多访问几次接口
http://127.0.0.1:8000/v1/blog/detail?id=12
,返回数据正常,我们多访问几次,查看三台服务的日志,均收到了请求
jwt实现权限校验
一般情况下,上游api服务都需要客户端有身份验证,并且不影响错误的请求或者无认证的请求通过,那么此时,我们可以利用kong的jwt插件来实现,直接在网关这一层过滤掉请求
consumers
一个consumer可以代表一个微服务或者一个应用。为什么?因为你想给一个应用配置插件服务的话,比如说jwt认证,这个插件怎么样才能作用到这个应用上面呢?就是需要创建一个consumer,插件作用于consumer,consumer绑定应用。
- 接下来我们创建一个consumer
- 添加jwt认证
- 全局配置jwt,配置header头的token名
- 此时我们再来访问
http://127.0.0.1:8000/v1/blog/detail?id=12
,已经不通过了
- 那么我们先手动构造一个token来验证一下,有两点需要注意,一个是jwt,是我们配置的验证名称,一个是iss
- 我们通过
https://jwt.io/
生成token,payload如下,注意secret去consumer中获取
{"sub": "1234567890","name": "John Doe","iat": 1516239022,"iss":"jwt"
}
项目中引入jwt
- 关于怎么使用jwt,我在jwt讲解这篇文章中说过。
- 注意两个地方,一个是jwt的秘钥kong和gin必须保持一致
- 一个是issuer必须保持一致,相关代码如下
package middlewareimport ("gin-demo/service""github.com/gin-gonic/gin""github.com/golang-jwt/jwt/v5""log""strings""time"
)// 定义自己的秘钥 所有的服务必须用一个秘钥才能正确解析token
// 注意注意:这个秘钥必须和kong保持一致
var privateKey = []byte("FLHzZzGqZPlSzKgNyq4wXg4bKUhFRsH1")// UserClaims 我们声明一个结构体,里面包含我们想要保存的信息
type UserClaims struct {Uid int64jwt.RegisteredClaims // 内嵌标准的声明
}// GenToken 生成token
func GenToken(uid int64) (string, error) {//初始化结构体claims := UserClaims{Uid: uid,RegisteredClaims: jwt.RegisteredClaims{//设置过期时间ExpiresAt: jwt.NewNumericDate(time.Now().Add(time.Second * 3600)),//颁发时间IssuedAt: jwt.NewNumericDate(time.Now()),//主题Subject: "Token",//注意这里 发行人要和kong保持一致Issuer: "jwt",},}//生成token 使用hs256 加密 结构体,然后再用秘钥对其做数字签名return jwt.NewWithClaims(jwt.SigningMethodHS256, claims).SignedString(privateKey)
}// 解析token
func ParseToken(c *gin.Context) {claims := new(UserClaims)xtoken := c.GetHeader("x-token")tokenString := strings.Split(xtoken, " ")if len(xtoken) == 0 || len(tokenString) < 2 {service.ErrorResponse(c, 9999, "请先登录!")return}log.Printf("解析到的token是:%v", tokenString)token, err := jwt.ParseWithClaims(tokenString[1], claims, keyFunc)log.Printf("解析到的token是:%v", err)if err != nil {c.Abort()service.ErrorResponse(c, 9999, "用户名密码错误!")return}//建议token是否有效if token.Valid {log.Printf("解析到的uid是:%d", claims.Uid)c.Set("uid", claims.Uid)c.Next()} else {c.Abort()service.ErrorResponse(c, 9999, "用户名密码错误!")return}
}func keyFunc(token *jwt.Token) (interface{}, error) {return privateKey, nil
}
-
结果
-
失败结果,kong直接拦截,并未到达服务层实例
流量控制
- 我们现在来配置一个每秒接收5个请求的限制
- 然后我们用jmeter测试一下,一秒内模拟10个用户发送10个请求
- 查看结果
黑白名单
- 我们可以选择指定给service或者route添加插件,下图我给route添加了插件
- 再次访问接口
总结
kong的相关功能就演示完毕了,其他功能比如反爬策略,协议转换感兴趣的小伙伴们可以自己探索一下。
相关参考
相关参考
相关参考
官方文档
中文文档
相关文档
相关文档
相关文章:

详讲api网关之kong的基本概念及安装和使用(二)
consul的服务注册与发现 如果不知道consul的使用,可以点击上方链接,这是我写的关于consul的一篇文档。 upstreamconsul实现负载均衡 我们知道,配置upstream可以实现负载均衡,而consul实现了服务注册与发现,那么接下来…...

取消Vscode在输入符号时自动补全
取消Vscode在输入符号时自动补全 取消Vscode在输入符号时自动补全问题演示解决方法 取消Vscode在输入符号时自动补全 问题演示 在此状态下输入/会直接自动补全, 如下图 笔者想要达到的效果为可以正常输入/而不进行补全, 如下图 解决方法 在设置->文本编辑器->建议, 取消…...

ElementUI Form:Input 输入框
ElementUI安装与使用指南 Input 输入框 点击下载learnelementuispringboot项目源码 效果图 el-input.vue 页面效果图 项目里el-input.vue代码 <script> export default {name: el_input,data() {return {input: ,input1: ,input2: ,input3: ,input4: ,textarea: …...

Vue_Router_守卫
路由守卫:路由进行权限控制。 分为:全局守卫,独享守卫,组件内守卫。 全局守卫 //创建并暴露 路由器 const routernew Vrouter({mode:"hash"//"hash路径出现#但是兼容性强,history没有#兼容性差"…...
GDB调试技巧实战--自动化画出类关系图
1. 前言 上节我们在帖子《Modern C++利用工具快速理解std::tuple的实现原理》根据GDB的ptype命令快速的理解了std::tuple数据结构的实现,但是手动一个个打印,然后手动画出的UML图,这个过程明显可以自动化。 本文旨在写一个GDB python脚本把这个过程自动化。 本脚本也可以用…...

python使用Schedule
目录 一:使用场景: 二:参数 三:实例 "Schedule"在Python中通常指的是时间调度或任务计划。Python中有多个库可以用来处理时间调度和任务计划,其中最流行的是schedule库。 一&#x…...

Linux系列之查看cpu、内存、磁盘使用情况
查看磁盘空间 df命令用于显示磁盘分区上的可使用的磁盘空间。默认显示单位为KB。可以利用该命令来获取硬盘被占用了多少空间,目前还剩下多少空间等信息。使用df -h命令,加个-h参数是为了显示GB MB KB单位,这样更容易查看 Filesystem …...

【C语言】socket编程接收问题
一、recv()函数接收到的返回值为0表示对端已经关闭 在TCP套接字编程中,通过recv()函数接收到的返回值为0通常表示对端已经关闭了套接字的发送部分。这是因为TCP是一个基于连接的协议,其中有定义明确的连接建立和终止流程;当对端调用close()或…...
Python与ArcGIS系列(二十)GDAL之合并shp和geojson要素图层
目录 0 简述1 代码实现2 结果展示0 简述 Shp格式是GIS中非常重要的数据格式,主要在Arcgis中使用,但在进行很多基于网页的空间数据可视化时,通常只接受GeoJSON格式的数据,众所周知JSON是利用键值对+嵌套来表示数据的一种格式,以其轻量、易解析的优点,被广泛使用与各种领域…...

CGAL5.4.1 边塌陷算法
目录 1、使用曲面网格的示例 2、使用默认多面体的示例 3、使用丰富多面体的示例 主要对1、使用曲面网格的示例 进行深度研究 CGAL编译与安装CGAL安装到验证到深入_cgal测试代码-CSDN博客 参考资料CGAL 5.4.5 - Triangulated Surface Mesh Simplification: User Manual …...

网络安全知识和华为防火墙
网络安全 网络空间安全 ---Cyberspace 2003年美国提出的网络空间概念 ---一个由信息基础设施组成的互相依赖的网络。 我国官方文件定义:网络空间为继海、陆、空、天以外的第五大人类互动领域。 通信保密阶段 --- 计算机安全阶段 --- 信息系统安全 --- 网络空间安…...

Docker 搭建MySQL主从复制-读写分离
一. 介绍 MySQL主从复制是一种常用的数据库高可用性解决方案,通过在主数据库上记录的数据变更,同步到一个或多个从数据库,实现数据的冗余备份和读写分离。在Docker环境下搭建MySQL主从复制和读写分离,不仅方便管理,还…...
[linux] which和find有什么区别?
which 和 find 都是 Unix/Linux 系统中的命令,但它们的用途和工作方式有很大的不同。 which 命令:which 命令是用来查找并显示用户可以在当前环境下执行的命令的完整路径。这些命令通常位于 PATH 环境变量中指定的目录中。例如,which python …...

使用Neo4j做技术血缘管理
目录 一、neo4j介绍 二、windows安装启动neo4j 2.1下载neo4j 2.2 解压文件 2.3 启动neo4j 三、neo4j基础操作 3.1 创建结点和关系 3.2 查询 3.3 更改 3.4 删除 四、技术血缘Demo实现 4.1 构建节点对象 4.2 构建存储对象 4.3 创建有属性关联关系 4.4 最后是图结果…...

Unity-WebGL
问题:提示gzip压缩报错解决:关闭打包的地方压缩,如下图问题:窗口未全屏解决:使用百分比画布替换固定尺寸画布 参考:新版Unity打包Webgl端进行屏幕自适应_unity webgl分辨率自适应-CSDN博客问题:…...

腾讯云部署vue+node项目
文章目录 一、安装宝塔二、vue项目部署三、node项目部署 前言: 关于项目部署,一开始也是找了很多资料,费了点时间,所以记录一下。希望能对各位有所帮助。 一、安装宝塔 1.首先在控制台,进入云服务器的终端界面 2.输入命令和密码获取权限,并且安装宝塔界面 yum install -y w…...

HBase表结构
HBase是非关系型数据库,是高可靠性、高性能、面向列、可伸缩、实时读写的分布式数据库。 HBase使用场景 大规模数据存储:如日志记录、数据库备份等。实时数据访问:如实时搜索、实时分析等。高性能读写:如高并发、低延迟的读写操…...
本人面试积累面试题更新中
本人面试积累面试题 1.事务的隔离级别 答:2024年1月30日 1.读已提交-----读取其他事务已经提交的数据 2.读未提交-----读取其他事务还未提交的数据–可能出现脏读 3.可重复读-----同一个事务多次读取同一个数据,尽可能的保证数据的一致性但是可能出现幻读 4.串行读------确保每…...
[经典面试题]169. 多数元素
题目描述 给定一个大小为 n 的数组 nums ,返回其中的多数元素。多数元素是指在数组中出现次数 大于 ⌊ n/2 ⌋ 的元素。 你可以假设数组是非空的,并且给定的数组总是存在多数元素。 示例 1: 输入:nums [3,2,3] 输出:3…...

Wireshark网络协议分析 - TCP协议
在我的博客阅读本文 文章目录 1. 基础2. 实战2.1. 用Go写一个简单的TCP服务器与客户端2.2. Wireshark抓包分析2.3. 限制数据包的大小——MSS与MTU2.4. 保证TCP的有序传输——Seq,Len与Ack2.5. TCP头标志位——URG,ACK,PSH,RST&…...

UE5 学习系列(二)用户操作界面及介绍
这篇博客是 UE5 学习系列博客的第二篇,在第一篇的基础上展开这篇内容。博客参考的 B 站视频资料和第一篇的链接如下: 【Note】:如果你已经完成安装等操作,可以只执行第一篇博客中 2. 新建一个空白游戏项目 章节操作,重…...

(LeetCode 每日一题) 3442. 奇偶频次间的最大差值 I (哈希、字符串)
题目:3442. 奇偶频次间的最大差值 I 思路 :哈希,时间复杂度0(n)。 用哈希表来记录每个字符串中字符的分布情况,哈希表这里用数组即可实现。 C版本: class Solution { public:int maxDifference(string s) {int a[26]…...
React Native 导航系统实战(React Navigation)
导航系统实战(React Navigation) React Navigation 是 React Native 应用中最常用的导航库之一,它提供了多种导航模式,如堆栈导航(Stack Navigator)、标签导航(Tab Navigator)和抽屉…...

基于ASP.NET+ SQL Server实现(Web)医院信息管理系统
医院信息管理系统 1. 课程设计内容 在 visual studio 2017 平台上,开发一个“医院信息管理系统”Web 程序。 2. 课程设计目的 综合运用 c#.net 知识,在 vs 2017 平台上,进行 ASP.NET 应用程序和简易网站的开发;初步熟悉开发一…...
线程同步:确保多线程程序的安全与高效!
全文目录: 开篇语前序前言第一部分:线程同步的概念与问题1.1 线程同步的概念1.2 线程同步的问题1.3 线程同步的解决方案 第二部分:synchronized关键字的使用2.1 使用 synchronized修饰方法2.2 使用 synchronized修饰代码块 第三部分ÿ…...
【SpringBoot】100、SpringBoot中使用自定义注解+AOP实现参数自动解密
在实际项目中,用户注册、登录、修改密码等操作,都涉及到参数传输安全问题。所以我们需要在前端对账户、密码等敏感信息加密传输,在后端接收到数据后能自动解密。 1、引入依赖 <dependency><groupId>org.springframework.boot</groupId><artifactId...

Opencv中的addweighted函数
一.addweighted函数作用 addweighted()是OpenCV库中用于图像处理的函数,主要功能是将两个输入图像(尺寸和类型相同)按照指定的权重进行加权叠加(图像融合),并添加一个标量值&#x…...

【项目实战】通过多模态+LangGraph实现PPT生成助手
PPT自动生成系统 基于LangGraph的PPT自动生成系统,可以将Markdown文档自动转换为PPT演示文稿。 功能特点 Markdown解析:自动解析Markdown文档结构PPT模板分析:分析PPT模板的布局和风格智能布局决策:匹配内容与合适的PPT布局自动…...
基于数字孪生的水厂可视化平台建设:架构与实践
分享大纲: 1、数字孪生水厂可视化平台建设背景 2、数字孪生水厂可视化平台建设架构 3、数字孪生水厂可视化平台建设成效 近几年,数字孪生水厂的建设开展的如火如荼。作为提升水厂管理效率、优化资源的调度手段,基于数字孪生的水厂可视化平台的…...
如何为服务器生成TLS证书
TLS(Transport Layer Security)证书是确保网络通信安全的重要手段,它通过加密技术保护传输的数据不被窃听和篡改。在服务器上配置TLS证书,可以使用户通过HTTPS协议安全地访问您的网站。本文将详细介绍如何在服务器上生成一个TLS证…...