程序员的快乐如此简单

最近在GitHub上发起了一个关于Beego框架的小插件的开源仓库,这一举动虽然看似微小,但其中的快乐和意义却是无法用言语表达的。

Beego是一个开源的Go语言Web框架,它采用了MVC架构模式,并集成了很多常用的功能和中间件。小插件是指与Beego框架配套使用的、可扩展的、独立的软件模块或组件。通过开发小插件,可以扩展Beego框架的功能,提高开发效率和代码可维护性。

Beego-Requestid是一种中间件(Middleware),用于在处理HTTP请求时,为每个请求生成一个唯一的ID,并将其附加到请求上下文中。这样,您可以在应用程序的其他地方方便地访问这个唯一的请求ID,从而更好地跟踪和调试应用程序。

使用RequestId中间件可以帮助您解决以下问题:

  1. 跟踪请求:通过在每个请求中添加唯一的ID,您可以轻松地在应用程序中跟踪请求的来源和路径。这对于调试和性能优化非常有用。
  2. 日志记录:您可以使用请求ID将日志记录与特定请求关联起来。这样,当您在日志中查找特定请求的信息时,可以更方便地定位相关的日志条目。
  3. 错误处理:如果应用程序中出现错误,请求ID可以帮助您识别是哪个请求引发了错误。这对于故障排查和问题报告非常有帮助。
代码

话不多说直接看源码:

go 复制代码
package beego_requestid

import (
	"github.com/beego/beego"
	"github.com/beego/beego/context"
	"github.com/google/uuid"
)

const DefaultHeaderReqIdKey = "X-Request-Id"

type Option func(config *Config)

type GenRequestIdFunc func() string

type Config struct {
	genRequestIdFunc               GenRequestIdFunc
	headerReqIdKey, customReqIdKey string
}

func NewFilter(opts ...Option) beego.FilterFunc {
	cnf := &Config{
		genRequestIdFunc: DefaultGenRequestIdFunc,
		headerReqIdKey:   DefaultHeaderReqIdKey,
	}

	for _, opt := range opts {
		opt(cnf)
	}

	return func(c *context.Context) {
		reqId := c.Request.Header.Get(cnf.headerReqIdKey)
		if reqId == "" {
			reqId = cnf.genRequestIdFunc()
			c.Request.Header.Add(cnf.headerReqIdKey, reqId)
		}
		if cnf.customReqIdKey != "" {
			c.Input.SetData(cnf.customReqIdKey, reqId)
		}
	}
}

func WithGenRequestIdFunc(genFunc GenRequestIdFunc) Option {
	return func(config *Config) {
		config.genRequestIdFunc = genFunc
	}
}

func WithHeaderReqIdKey(key string) Option {
	return func(config *Config) {
		config.headerReqIdKey = key
	}
}

func WithCustomReqIdKey(key string) Option {
	return func(config *Config) {
		config.customReqIdKey = key
	}
}

func DefaultGenRequestIdFunc() string {
	return uuid.NewString()
}

使用示例:

go 复制代码
package main

import (
	"log"
	"time"

	"github.com/spf13/cast"
	"github.com/beego/beego"
	"github.com/beego/beego/context"
	beego_requestid "github.com/ibarryyan/beego-requestid"
)

func example1() {
	beego.InsertFilter("/*", beego.BeforeRouter, beego_requestid.NewFilter())

	beego.Get("/hello", func(c *context.Context) {
		reqId := c.Request.Header.Get("X-Request-Id")
		log.Printf("reqestid = %s", reqId)

		_, _ = c.ResponseWriter.Write([]byte("hello..."))
		return
	})

	beego.Run(":9900")
}

func example2() {
	beego.InsertFilter("/*", beego.BeforeRouter, beego_requestid.NewFilter(
		beego_requestid.WithGenRequestIdFunc(func() string {
			return cast.ToString(time.Now().Unix())
		}),
		beego_requestid.WithHeaderReqIdKey("my_header_reqid"),
		beego_requestid.WithCustomReqIdKey("my_reqid"),
	))

	beego.Get("/hello", func(c *context.Context) {
		reqId := c.Request.Header.Get("my_header_reqid")
		log.Printf("reqestid = %s", reqId)

		cReqId := c.Input.GetData("my_reqid")
		log.Printf("my reqestid = %s", cReqId)

		_, _ = c.ResponseWriter.Write([]byte("hello..."))
		return
	})

	beego.Run(":9900")
}

此外,前端请求时需要带上header key要与后端的一致

获得快乐

发完代码后我就直接去Beego的GitHub仓库下提了一个issue,来分享的研究的中间件,地址:https://github.com/beego/beego/issues/5419,后来没想到竟然收到了回复,哈哈哈

然后我立马就去新的issue分享了我的插件

https://github.com/beego/beego/issues/5421

再后来,我就有两个star了~

仓库地址

https://github.com/ibarryyan/beego-requestid

相关推荐
STQY燊桐启元(深圳)电子科技2 小时前
医疗精密电源散热方案:相变陶瓷片保障医疗设备长效稳定低干扰
大数据·网络·人工智能
CDN3604 小时前
节点智能调度实操:解决出海区域访问快慢不均、节点拥堵、跨洋延迟高,CDN 全网择优落地方案
运维·服务器·网络
roman_日积跬步-终至千里5 小时前
【数据治理(6)】DataOps 不是调度工具,而是让数据产品长期可信的运行机制
java·服务器·网络
可乐鸡翅yeah_7 小时前
个人 / 外包流媒体项目交付实战,M3U8 验收与问题闭环完整工作流
运维·网络·python·低代码·django·m3u8·在线播放
黄俊懿8 小时前
【架构师从入门到进阶】第五章:DNS&CDN&网关优化思路——第十节:网关安全-单向加密
网络·数据库·计算机网络·安全·架构·系统架构·架构师
蓝宝石的傻话8 小时前
因为MiBeeNVR,决定接 onvif-go 自己管理并重构
数码相机·重构·golang
Patrick在香港8 小时前
Python 拉取城巴开放数据:406 条路线,香港岛巴士网络的数字画像
网络·python·数据分析·php·数据可视化·香港·开放数据
一直C9 小时前
Linux系统编程|进程间通信IPC全套详解(1)(管道、信号)
linux·c语言·开发语言·网络·青少年编程·visual studio code
Experience-摆渡9 小时前
自建 IP 轮换方案实战:健康探测 + 熔断剔除 + 粘性会话
网络·网络协议·tcp/ip
luj_17689 小时前
合法避税与投资评估实战指南
c语言·开发语言·网络·经验分享·算法