wireguard-dashboard/middleware/system_log.go

108 lines
2.6 KiB
Go
Raw Normal View History

2024-06-03 17:09:45 +08:00
package middleware
import (
"bytes"
"gitee.ltd/lxh/logger/log"
"github.com/gin-gonic/gin"
jsoniter "github.com/json-iterator/go"
"io"
"regexp"
"strings"
"time"
"wireguard-dashboard/model/entity"
"wireguard-dashboard/repository"
)
// bodyWriter
// @description: 重写ResponseBody
type bodyWriter struct {
gin.ResponseWriter
body *bytes.Buffer
}
func SystemLogRequest() gin.HandlerFunc {
return func(c *gin.Context) {
var userId string
if userInfo, ok := c.Get("user"); ok {
userId = userInfo.(*entity.User).Id
}
// 开始时间
start := time.Now()
host := c.Request.Host // 请求域名
path := c.Request.URL.Path // 接口地址
query := c.Request.URL.RawQuery // 参数
if strings.Contains(path, "/api/dashboard/list") {
c.Next()
return
}
var bodyStr string
if !strings.Contains(path, "/api/login") {
body, err := c.GetRawData() // body参数
if err == nil {
bodyStr = string(body)
c.Request.Body = io.NopCloser(bytes.NewBuffer(body))
reg := regexp.MustCompile("\\s+")
bodyStr = reg.ReplaceAllString(bodyStr, "")
}
}
method := c.Request.Method // 请求方式
ip := c.ClientIP() // 取出IP
// 处理实际客户端IP
if c.Request.Header.Get("U-Real-Ip") != "" {
ip = c.Request.Header.Get("U-Real-Ip") // 这个是网关Nginx自定义的Header头
} else if c.Request.Header.Get("U-Forwarded-For") != "" {
ip = c.Request.Header.Get("U-Forwarded-For") // 这个是网关Nginx自定义的Header头
}
ua := c.Request.UserAgent() // UA
// 重写客户端IP
c.Request.Header.Set("X-Forwarded-For", ip)
c.Request.Header.Set("X-Real-Ip", ip)
// 拦截response
bw := &bodyWriter{body: bytes.NewBufferString(""), ResponseWriter: c.Writer}
c.Writer = bw
header := c.Request.Header
headerStr, _ := jsoniter.MarshalToString(header)
// 执行下一步请求
c.Next()
// 计算耗时
cost := time.Since(start).Milliseconds()
// 组装实体
l := entity.SystemLog{
UserId: userId,
ClientIP: ip,
Host: host,
Method: method,
Uri: path,
Header: headerStr,
Body: bodyStr,
Form: "",
Query: query,
UserAgent: ua,
Cost: cost,
StatusCode: c.Writer.Status(),
Response: "",
}
// 如果不是返回200把返回值保存一下
if c.Writer.Status() != 200 {
resp := bw.body.String()
l.Response = resp
}
go func() {
if er := repository.SystemLog().SaveLog(&l); er != nil {
log.Debugf("请求日志: %+v", l)
log.Errorf("保存请求日志失败: %v", er)
}
}()
}
}