diff --git a/define/response.go b/define/response.go index 82076bd..b774eef 100644 --- a/define/response.go +++ b/define/response.go @@ -7,31 +7,13 @@ // Date : 2022-06-25 20:33 package define +import ( + "git.zhangdeman.cn/zhangdeman/consts" + "git.zhangdeman.cn/zhangdeman/wrapper" +) + var ( - // RequestIDField 请求ID - RequestIDField = "request_id" - // TraceIDField 追踪ID - TraceIDField = "trace_id" - // StartRequestTimeField 开始请求时间字段 - StartRequestTimeField = "start_request_time" - // FinishRequestTimeField 完成请求时间 - FinishRequestTimeField = "finish_request_time" - // ResponseCodeField 响应状态码字段 - ResponseCodeField = "code" - // ResponseMessageField 响应信息字段 - ResponseMessageField = "message" - // HandleRequestCostField 处理请求耗时 - HandleRequestCostField = "cost" - // ResponseDataField 响应数据字段 - ResponseDataField = "data" - // ResponseTraceIDField 响应TraceID字段 - ResponseTraceIDField = "trace_id" - // ResponseRequestIDField 响应的请求ID字段 - ResponseRequestIDField = "request_id" - // RecordResponseDataField 记录响应数据到上下文 - RecordResponseDataField = "pkg_gin_record_response_data" - // RecordRequestDataField 记录请求数据到上下文 - RecordRequestDataField = "pkg_gin_record_request_data" + inputHttpHandleConfig = &HttpHandleConfig{} ) // HttpHandleConfig 请求处理配置 @@ -40,15 +22,17 @@ var ( // // Date : 20:41 2022/6/25 type HttpHandleConfig struct { - RequestIDField string - TraceIDField string - ResponseCodeField string - ResponseMessageField string - HandleRequestCostField string - ResponseDataField string - ResponseTraceIDField string - ResponseRequestIDField string - StartRequestTimeField string + RecordRequestDataField string + RecordResponseDataField string + RequestIDField string + TraceIDField string + ResponseCodeField string + ResponseMessageField string + HandleRequestCostField string + ResponseDataField string + ResponseTraceIDField string + StartRequestTimeField string + FinishRequestTimeField string } // ConvertDefaultConfig 覆盖默认配置 @@ -57,39 +41,70 @@ type HttpHandleConfig struct { // // Date : 20:41 2022/6/25 func ConvertDefaultConfig(cfg *HttpHandleConfig) { - if len(cfg.RequestIDField) > 0 { - RequestIDField = cfg.ResponseRequestIDField - } + inputHttpHandleConfig = cfg +} - if len(cfg.TraceIDField) > 0 { - TraceIDField = cfg.TraceIDField - } - - if len(cfg.ResponseCodeField) > 0 { - ResponseCodeField = cfg.ResponseCodeField - } - - if len(cfg.ResponseMessageField) > 0 { - ResponseMessageField = cfg.ResponseMessageField - } - - if len(cfg.ResponseDataField) > 0 { - ResponseDataField = cfg.ResponseDataField - } - - if len(cfg.ResponseRequestIDField) > 0 { - ResponseRequestIDField = cfg.ResponseRequestIDField - } - - if len(cfg.ResponseTraceIDField) > 0 { - ResponseTraceIDField = cfg.ResponseTraceIDField - } - - if len(cfg.HandleRequestCostField) > 0 { - HandleRequestCostField = cfg.HandleRequestCostField - } - - if len(cfg.StartRequestTimeField) > 0 { - StartRequestTimeField = cfg.StartRequestTimeField +// GetHttpHandleConfig 获取http配置 +// +// Author : go_developer@163.com<白茶清欢> +// +// Date : 16:55 2024/7/23 +func GetHttpHandleConfig() *HttpHandleConfig { + return &HttpHandleConfig{ + RequestIDField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.RequestIDField == "", + consts.GinRequestIDField, + wrapper.String(inputHttpHandleConfig.RequestIDField), + ).Value(), + TraceIDField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.TraceIDField == "", + consts.GinTraceIDField, + wrapper.String(inputHttpHandleConfig.TraceIDField), + ).Value(), + ResponseCodeField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.ResponseCodeField == "", + consts.GinResponseCodeField, + wrapper.String(inputHttpHandleConfig.ResponseCodeField), + ).Value(), + ResponseMessageField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.ResponseMessageField == "", + consts.GinResponseMessageField, + wrapper.String(inputHttpHandleConfig.ResponseMessageField), + ).Value(), + HandleRequestCostField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.HandleRequestCostField == "", + consts.GinHandleRequestCostField, + wrapper.String(inputHttpHandleConfig.HandleRequestCostField), + ).Value(), + ResponseDataField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.ResponseDataField == "", + consts.GinResponseDataField, + wrapper.String(inputHttpHandleConfig.ResponseDataField), + ).Value(), + ResponseTraceIDField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.ResponseTraceIDField == "", + consts.GinResponseTraceIDField, + wrapper.String(inputHttpHandleConfig.ResponseTraceIDField), + ).Value(), + StartRequestTimeField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.StartRequestTimeField == "", + consts.GinStartRequestTimeField, + wrapper.String(inputHttpHandleConfig.StartRequestTimeField), + ).Value(), + FinishRequestTimeField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.FinishRequestTimeField == "", + consts.GinFinishRequestTimeField, + wrapper.String(inputHttpHandleConfig.FinishRequestTimeField), + ).Value(), + RecordRequestDataField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.RecordRequestDataField == "", + consts.GinRecordRequestDataField, + wrapper.String(inputHttpHandleConfig.RecordRequestDataField), + ).Value(), + RecordResponseDataField: wrapper.TernaryOperator.String( + nil == inputHttpHandleConfig || inputHttpHandleConfig.RecordResponseDataField == "", + consts.GinRecordResponseDataField, + wrapper.String(inputHttpHandleConfig.RecordResponseDataField), + ).Value(), } } diff --git a/go.mod b/go.mod index f62b322..ad25b7d 100644 --- a/go.mod +++ b/go.mod @@ -5,7 +5,9 @@ go 1.21 toolchain go1.21.5 require ( + git.zhangdeman.cn/zhangdeman/consts v0.0.0-20240726024939-e424db29c5c4 git.zhangdeman.cn/zhangdeman/exception v0.0.0-20231105153815-e8561a060cc8 + git.zhangdeman.cn/zhangdeman/logger v0.0.0-20240725055115-98eb52ae307a git.zhangdeman.cn/zhangdeman/network v0.0.0-20230925112156-f0eb86dd2442 git.zhangdeman.cn/zhangdeman/wrapper v0.0.0-20240627031706-9ff1c213bb50 github.com/gin-gonic/gin v1.10.0 @@ -14,11 +16,12 @@ require ( ) require ( - git.zhangdeman.cn/zhangdeman/consts v0.0.0-20240719075638-afb5d1d933ce // indirect + git.zhangdeman.cn/zhangdeman/easylock v0.0.0-20230731062340-983985c12eda // indirect git.zhangdeman.cn/zhangdeman/easymap v0.0.0-20240311030808-e2a2e6a3c211 // indirect git.zhangdeman.cn/zhangdeman/op_type v0.0.0-20240122104027-4928421213c0 // indirect git.zhangdeman.cn/zhangdeman/serialize v0.0.0-20240618035451-8d48a6bd39dd // indirect git.zhangdeman.cn/zhangdeman/util v0.0.0-20240618042405-6ee2c904644e // indirect + git.zhangdeman.cn/zhangdeman/websocket v0.0.0-20240723075210-85feada512b2 // indirect github.com/BurntSushi/toml v1.4.0 // indirect github.com/axgle/mahonia v0.0.0-20180208002826-3358181d7394 // indirect github.com/bytedance/sonic v1.11.9 // indirect @@ -32,9 +35,12 @@ require ( github.com/go-playground/locales v0.14.1 // indirect github.com/go-playground/universal-translator v0.18.1 // indirect github.com/goccy/go-json v0.10.3 // indirect + github.com/gorilla/websocket v1.5.3 // indirect github.com/json-iterator/go v1.1.12 // indirect github.com/klauspost/cpuid/v2 v2.2.8 // indirect github.com/leodido/go-urn v1.4.0 // indirect + github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible // indirect + github.com/lestrrat-go/strftime v1.0.6 // indirect github.com/mattn/go-isatty v0.0.20 // indirect github.com/mitchellh/go-homedir v1.1.0 // indirect github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect @@ -42,6 +48,7 @@ require ( github.com/mozillazg/go-pinyin v0.20.0 // indirect github.com/mssola/user_agent v0.6.0 // indirect github.com/pelletier/go-toml/v2 v2.2.2 // indirect + github.com/pkg/errors v0.9.1 // indirect github.com/spaolacci/murmur3 v1.1.0 // indirect github.com/tidwall/gjson v1.17.1 // indirect github.com/tidwall/match v1.1.1 // indirect @@ -55,5 +62,6 @@ require ( golang.org/x/sys v0.22.0 // indirect golang.org/x/text v0.16.0 // indirect google.golang.org/protobuf v1.34.2 // indirect + gopkg.in/olahol/melody.v1 v1.0.0-20170518105555-d52139073376 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect ) diff --git a/go.sum b/go.sum index 6ca8741..e7cdf84 100644 --- a/go.sum +++ b/go.sum @@ -1,9 +1,13 @@ -git.zhangdeman.cn/zhangdeman/consts v0.0.0-20240719075638-afb5d1d933ce h1:DH01rT/F/UNMqXm5HIv+Q2oKPSkg8rjy1TK8pE83rpU= -git.zhangdeman.cn/zhangdeman/consts v0.0.0-20240719075638-afb5d1d933ce/go.mod h1:IXXaZkb7vGzGnGM5RRWrASAuwrVSNxuoe0DmeXx5g6k= +git.zhangdeman.cn/zhangdeman/consts v0.0.0-20240726024939-e424db29c5c4 h1:mibnyzYbZullK0aTHVASHl3UeoVr8IgytQZsuyv+yEM= +git.zhangdeman.cn/zhangdeman/consts v0.0.0-20240726024939-e424db29c5c4/go.mod h1:IXXaZkb7vGzGnGM5RRWrASAuwrVSNxuoe0DmeXx5g6k= +git.zhangdeman.cn/zhangdeman/easylock v0.0.0-20230731062340-983985c12eda h1:bMD6r9gjRy7cO+T4zRQVYAesgIblBdTnhzT1vN5wjvI= +git.zhangdeman.cn/zhangdeman/easylock v0.0.0-20230731062340-983985c12eda/go.mod h1:dT0rmHcJ9Z9IqWeMIt7YzR88nKkNV2V3dfG0j9Q6lK0= git.zhangdeman.cn/zhangdeman/easymap v0.0.0-20240311030808-e2a2e6a3c211 h1:I/wOsRpCSRkU9vo1u703slQsmK0wnNeZzsWQOGtIAG0= git.zhangdeman.cn/zhangdeman/easymap v0.0.0-20240311030808-e2a2e6a3c211/go.mod h1:SrtvrQRdzt+8KfYzvosH++gWxo2ShPTzR1m3VQ6uX7U= git.zhangdeman.cn/zhangdeman/exception v0.0.0-20231105153815-e8561a060cc8 h1:q9pXs8ByVg/XwyDopIGyfEOi/LyHFR0r1rCnJ90uFxw= git.zhangdeman.cn/zhangdeman/exception v0.0.0-20231105153815-e8561a060cc8/go.mod h1:Voc8J4ordx7nuMWpgACXXZULQy7ZIuBzcEIoS8VnDIw= +git.zhangdeman.cn/zhangdeman/logger v0.0.0-20240725055115-98eb52ae307a h1:22VkxGmpS58zHA8tf75lPr/3S6hmHKP00w/jUa700Ps= +git.zhangdeman.cn/zhangdeman/logger v0.0.0-20240725055115-98eb52ae307a/go.mod h1:phaF6LMebn7Fpp8J/mOzHRYGniKuCk78k4N53T2m8NI= git.zhangdeman.cn/zhangdeman/network v0.0.0-20230925112156-f0eb86dd2442 h1:1eBf0C0gdpBQOqjTK3UCw/mwzQ/SCodx3iTQtidx9eE= git.zhangdeman.cn/zhangdeman/network v0.0.0-20230925112156-f0eb86dd2442/go.mod h1:hFYWiS+ExIuJJJdwHWy4P3pVHbd/0mpv53qlbhDNdTI= git.zhangdeman.cn/zhangdeman/op_type v0.0.0-20240122104027-4928421213c0 h1:gUDlQMuJ4xNfP2Abl1Msmpa3fASLWYkNlqDFF/6GN0Y= @@ -12,6 +16,8 @@ git.zhangdeman.cn/zhangdeman/serialize v0.0.0-20240618035451-8d48a6bd39dd h1:2Y3 git.zhangdeman.cn/zhangdeman/serialize v0.0.0-20240618035451-8d48a6bd39dd/go.mod h1:6+7whkCmb4sJDIfH3HxNuXRveaM0gCCNWd2uXZqNtIE= git.zhangdeman.cn/zhangdeman/util v0.0.0-20240618042405-6ee2c904644e h1:Q973S6CcWr1ICZhFI1STFOJ+KUImCl2BaIXm6YppBqI= git.zhangdeman.cn/zhangdeman/util v0.0.0-20240618042405-6ee2c904644e/go.mod h1:VpPjBlwz8U+OxZuxzHQBv1aEEZ3pStH6bZvT21ADEbI= +git.zhangdeman.cn/zhangdeman/websocket v0.0.0-20240723075210-85feada512b2 h1:P2kuhU2TFWk9mPbJlZCK6FMDVS7S3NGafWKD4eNqKiI= +git.zhangdeman.cn/zhangdeman/websocket v0.0.0-20240723075210-85feada512b2/go.mod h1:7KaMpQmWgiNLpEkaV7oDtep7geI1f/VoCoPVcyvMjAE= git.zhangdeman.cn/zhangdeman/wrapper v0.0.0-20240627031706-9ff1c213bb50 h1:olo34i2Gq5gX7bYPv5TR4X5l5CrYFtu9UCElkYlmL2c= git.zhangdeman.cn/zhangdeman/wrapper v0.0.0-20240627031706-9ff1c213bb50/go.mod h1:US/pcq2vstE3iyxIHf53w8IeXKkZys7bj/ozLWkRYeE= github.com/BurntSushi/toml v1.4.0 h1:kuoIxZQy2WRRk1pttg9asf+WVv6tWQuBNVmK8+nqPr0= @@ -49,9 +55,13 @@ github.com/go-playground/validator/v10 v10.22.0 h1:k6HsTZ0sTnROkhS//R0O+55JgM8C4 github.com/go-playground/validator/v10 v10.22.0/go.mod h1:dbuPbCMFw/DrkbEynArYaCwl3amGuJotoKCe95atGMM= github.com/goccy/go-json v0.10.3 h1:KZ5WoDbxAIgm2HNbYckL0se1fHD6rz5j4ywS6ebzDqA= github.com/goccy/go-json v0.10.3/go.mod h1:oq7eo15ShAhp70Anwd5lgX2pLfOS3QCiwU/PULtXL6M= -github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU= -github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.6 h1:BKbKCqvP6I+rmFHt06ZmyQtvB8xAkWdhFyr0ZUNZcxQ= +github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= +github.com/gorilla/websocket v1.5.3 h1:saDtZ6Pbx/0u+bgYQ3q96pZgCzfhKXGPqt7kZ72aNNg= +github.com/gorilla/websocket v1.5.3/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= +github.com/jonboulle/clockwork v0.3.0 h1:9BSCMi8C+0qdApAp4auwX0RkLGUjs956h0EkuQymUhg= +github.com/jonboulle/clockwork v0.3.0/go.mod h1:Pkfl5aHPm1nk2H9h0bjmnJD/BcgbGXUBGnn1kMkgxc8= github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= @@ -60,6 +70,12 @@ github.com/klauspost/cpuid/v2 v2.2.8/go.mod h1:Lcz8mBdAVJIBVzewtcLocK12l3Y+JytZY github.com/knz/go-libedit v1.10.1/go.mod h1:MZTVkCWyz0oBc7JOWP3wNAzd002ZbM/5hgShxwh4x8M= github.com/leodido/go-urn v1.4.0 h1:WT9HwE9SGECu3lg4d/dIA+jxlljEa1/ffXKmRjqdmIQ= github.com/leodido/go-urn v1.4.0/go.mod h1:bvxc+MVxLKB4z00jd1z+Dvzr47oO32F/QSNjSBOlFxI= +github.com/lestrrat-go/envload v0.0.0-20180220234015-a3eb8ddeffcc h1:RKf14vYWi2ttpEmkA4aQ3j4u9dStX2t4M8UM6qqNsG8= +github.com/lestrrat-go/envload v0.0.0-20180220234015-a3eb8ddeffcc/go.mod h1:kopuH9ugFRkIXf3YoqHKyrJ9YfUFsckUU9S7B+XP+is= +github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible h1:Y6sqxHMyB1D2YSzWkLibYKgg+SwmyFU9dF2hn6MdTj4= +github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible/go.mod h1:ZQnN8lSECaebrkQytbHj4xNgtg8CR7RYXnPok8e0EHA= +github.com/lestrrat-go/strftime v1.0.6 h1:CFGsDEt1pOpFNU+TJB0nhz9jl+K0hZSLE205AhTIGQQ= +github.com/lestrrat-go/strftime v1.0.6/go.mod h1:f7jQKgV5nnJpYgdEasS+/y7EsTb8ykN2z68n3TtcTaw= github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY= github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y= github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y= @@ -75,6 +91,8 @@ github.com/mssola/user_agent v0.6.0 h1:uwPR4rtWlCHRFyyP9u2KOV0u8iQXmS7Z7feTrstQw github.com/mssola/user_agent v0.6.0/go.mod h1:TTPno8LPY3wAIEKRpAtkdMT0f8SE24pLRGPahjCH4uw= github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM= github.com/pelletier/go-toml/v2 v2.2.2/go.mod h1:1t835xjRzz80PqgE6HHgN2JOsmgYu/h4qDAS4n929Rs= +github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= +github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI= @@ -127,6 +145,8 @@ google.golang.org/protobuf v1.34.2 h1:6xV6lTsCfpGD21XK49h7MhtcApnLqkfYgPcdHftf6h google.golang.org/protobuf v1.34.2/go.mod h1:qYOHts0dSfpeUzUFpOMr/WGzszTmLH+DiWniOlNbLDw= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/olahol/melody.v1 v1.0.0-20170518105555-d52139073376 h1:sY2a+y0j4iDrajJcorb+a0hJIQ6uakU5gybjfLWHlXo= +gopkg.in/olahol/melody.v1 v1.0.0-20170518105555-d52139073376/go.mod h1:BHKOc1m5wm8WwQkMqYBoo4vNxhmF7xg8+xhG8L+Cy3M= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/middleware/access_log.go b/middleware/access_log.go index c30f118..4411b65 100644 --- a/middleware/access_log.go +++ b/middleware/access_log.go @@ -8,13 +8,15 @@ package middleware import ( - "git.zhangdeman.cn/zhangdeman/wrapper" + "git.zhangdeman.cn/zhangdeman/consts" + "git.zhangdeman.cn/zhangdeman/gin/request" + "go.uber.org/zap" "strings" "git.zhangdeman.cn/zhangdeman/gin/define" + "git.zhangdeman.cn/zhangdeman/logger" "github.com/gin-gonic/gin" - "go.uber.org/zap" ) // fillCfg 填充默认配置 @@ -29,19 +31,12 @@ func fillCfg(cfg *AccessConfig) { if nil == cfg.IsRecordLog { cfg.IsRecordLog = defaultIsRecordLog } - if nil == cfg.ExtraFieldList { - cfg.ExtraFieldList = make([]string, 0) - } if nil == cfg.RequestHeaderList { cfg.RequestHeaderList = make([]string, 0) } if nil == cfg.ResponseHeaderList { cfg.ResponseHeaderList = make([]string, 0) } - if nil == cfg.ExtraFieldList { - cfg.ExtraFieldList = make([]string, 0) - } - cfg.ExtraFieldList = append(cfg.ExtraFieldList, define.RecordRequestDataField, define.RecordResponseDataField) } // getLogRequestHeader 获取记录的请求header @@ -54,7 +49,7 @@ func getLogRequestHeader(ctx *gin.Context, cfg *AccessConfig) map[string][]strin headerTable := make(map[string][]string) if len(cfg.RequestHeaderList) == 0 { // 全部记录 - for headerKey, _ := range ctx.Request.Header { + for headerKey := range ctx.Request.Header { cfg.RequestHeaderList = append(cfg.RequestHeaderList, headerKey) } } @@ -74,7 +69,7 @@ func getLogResponseHeader(ctx *gin.Context, cfg *AccessConfig) map[string][]stri responseHeaderTable := make(map[string][]string) if len(cfg.ResponseHeaderList) == 0 { // 全部记录 - for headerKey, _ := range ctx.Writer.Header() { + for headerKey := range ctx.Writer.Header() { cfg.ResponseHeaderList = append(cfg.ResponseHeaderList, headerKey) } zap.Any("pkg_gin_response_header", ctx.Writer.Header()) @@ -92,45 +87,34 @@ func getLogResponseHeader(ctx *gin.Context, cfg *AccessConfig) map[string][]stri // Date : 10:55 2022/7/14 func LogRequest(cfg *AccessConfig) gin.HandlerFunc { fillCfg(cfg) + handleConfig := define.GetHttpHandleConfig() return func(ctx *gin.Context) { // 未传入配置或者未传入日志实例 - if nil == cfg || nil == cfg.Logger || !cfg.IsRecordLog(ctx) { + if nil == cfg || nil == cfg.Logger || (nil != cfg.IsRecordLog && !cfg.IsRecordLog(ctx)) { ctx.Next() return } + startRequestTime := request.WrapperHandle.GetCtxIntData(ctx, handleConfig.StartRequestTimeField, 0) + // 记录请求日志 + logData := logger.NewLogData(ctx, consts.LogTypeRequest, "", map[string]any{ + handleConfig.StartRequestTimeField: startRequestTime, // 开始请求时间 + "request_header": getLogRequestHeader(ctx, cfg), // 请求header + "request_query": request.WrapperHandle.GetQuery(ctx), // 获取请求query + "request_body": request.WrapperHandle.GetRequestBody(ctx), // 请求body + }) + cfg.Logger.Info("接口请求日志记录", logger.ZapLogDataList(logData)...) ctx.Next() - startRequestTime := wrapper.OwnTime(ctx.GetTime(define.StartRequestTimeField)) - logDataList := []zap.Field{ - // 开始请求时间 - zap.Any(define.StartRequestTimeField, startRequestTime.FormatUnixMilli()), - } // 结束时间 - finishRequestTime := wrapper.OwnTime(ctx.GetTime(define.FinishRequestTimeField)) - logDataList = append( - logDataList, - zap.Any(define.FinishRequestTimeField, finishRequestTime.FormatUnixMilli()), // 请求完成时间 - zap.Int64("pkg_gin_request_cost", finishRequestTime.UnixMilli()-startRequestTime.UnixMilli()), // 接口耗时 - zap.Any("pkg_gin_request_header", getLogRequestHeader(ctx, cfg)), // 请求header - zap.Any("pkg_gin_response_header", getLogResponseHeader(ctx, cfg)), // 响应header - ) - - // 扩展数据 - for _, field := range cfg.ExtraFieldList { - val, _ := ctx.Get(field) - logDataList = append(logDataList, zap.Any(field, val)) - } - cfg.Logger.Info("请求日志记录", logDataList...) - if nil == cfg.FinishHook { - return - } - // hook 不为nil, 自动触发 - cfg.FinishHook( - ctx, - []byte(ctx.GetString(define.RecordRequestDataField)), - ctx.GetStringMap(define.RecordResponseDataField), - finishRequestTime.UnixMilli()-startRequestTime.UnixMilli(), - ) - + finishRequestTime := request.WrapperHandle.GetCtxIntData(ctx, handleConfig.FinishRequestTimeField, 0) + ctx.Set(handleConfig.FinishRequestTimeField, finishRequestTime) + // 记录相应日志 + logResponseData := logger.NewLogData(ctx, consts.LogTypeOutput, "", map[string]any{ + handleConfig.FinishRequestTimeField: finishRequestTime, // 完成请求时间 + "request_cost": finishRequestTime - startRequestTime, // 请求耗时 + "response_body": request.WrapperHandle.GetResponseBody(ctx, handleConfig.ResponseDataField, map[string]any{}), // 响应body + "response_header": getLogResponseHeader(ctx, cfg), // 响应header + }) + cfg.Logger.Info("接口响应日志记录", logger.ZapLogDataList(logResponseData)...) } } @@ -140,12 +124,10 @@ func LogRequest(cfg *AccessConfig) gin.HandlerFunc { // // Date : 11:26 2022/7/14 type AccessConfig struct { - Logger *zap.Logger // 日志实例 - RequestHeaderList []string // 要记录哪些header , 不传全部记录 - ResponseHeaderList []string // 要记录哪些响应header, 不传全部记录 - IsRecordLog func(ctx *gin.Context) bool // 验证当前请求是否记录日志 - ExtraFieldList []string // 记录的扩展字段列表,请将相关数据使用 ctx.Set 写入上下文中, 日志会自动记录 - FinishHook func(ctx *gin.Context, requestData []byte, responseData map[string]interface{}, cost int64) // 请求处理完成之后, 触发的hook函数 + Logger *zap.Logger // 日志实例 + RequestHeaderList []string // 要记录哪些header , 不传全部记录 + ResponseHeaderList []string // 要记录哪些响应header, 不传全部记录 + IsRecordLog func(ctx *gin.Context) bool // 验证当前请求是否记录日志 } // defaultIsRecordLog 默认仅记录 json api 日志 diff --git a/middleware/hook_after_response.go b/middleware/hook_after_response.go new file mode 100644 index 0000000..f1487a4 --- /dev/null +++ b/middleware/hook_after_response.go @@ -0,0 +1,38 @@ +// Package middleware ... +// +// Description : middleware ... +// +// Author : go_developer@163.com<白茶清欢> +// +// Date : 2024-07-26 11:54 +package middleware + +import ( + "git.zhangdeman.cn/zhangdeman/gin/define" + "git.zhangdeman.cn/zhangdeman/gin/request" + "github.com/gin-gonic/gin" +) + +type HookFunc func(ctx *gin.Context, requestData []byte, responseData map[string]interface{}, cost int64) + +// HookAfterResponseMiddleware 请求最终处理完成之后执行的中间件 +// +// Author : go_developer@163.com<白茶清欢> +// +// Date : 11:55 2024/7/26 +func HookAfterResponseMiddleware(hookFunc HookFunc) gin.HandlerFunc { + handleConfig := define.GetHttpHandleConfig() + return func(ctx *gin.Context) { + ctx.Next() + if nil == hookFunc { + return + } + // hook 不为nil, 自动触发 + hookFunc( + ctx, + []byte(ctx.GetString(handleConfig.RecordRequestDataField)), + ctx.GetStringMap(handleConfig.RecordResponseDataField), + request.WrapperHandle.GetCtxIntData(ctx, handleConfig.StartRequestTimeField, 0)-request.WrapperHandle.GetCtxIntData(ctx, handleConfig.StartRequestTimeField, 0), + ) + } +} diff --git a/middleware/init_request.go b/middleware/init_request.go index 0b12a34..61bb406 100644 --- a/middleware/init_request.go +++ b/middleware/init_request.go @@ -27,11 +27,12 @@ import ( // Date : 23:08 2022/6/25 func InitRequest() gin.HandlerFunc { return func(ctx *gin.Context) { + httpHandleConfig := define.GetHttpHandleConfig() traceID := getTraceID(ctx) requestID := getRequestID(ctx, traceID) - ctx.Set(define.TraceIDField, traceID) - ctx.Set(define.RequestIDField, requestID) - ctx.Set(define.StartRequestTimeField, time.Now()) + ctx.Set(httpHandleConfig.TraceIDField, traceID) + ctx.Set(httpHandleConfig.RequestIDField, requestID) + ctx.Set(httpHandleConfig.StartRequestTimeField, time.Now().UnixMilli()) ctx.Next() } } @@ -57,7 +58,7 @@ func getTraceID(ctx *gin.Context) string { // // Date : 23:12 2022/6/25 func getRequestID(ctx *gin.Context, traceID string) string { - requestID := ctx.GetHeader("X-Forward-Request-ID") + requestID := ctx.GetHeader("X-Forward-Request-Id") if len(requestID) > 0 { return requestID } diff --git a/request/form.go b/request/form.go index 030d15e..6d2594d 100644 --- a/request/form.go +++ b/request/form.go @@ -36,10 +36,10 @@ type form struct { // // Date : 00:34 2022/7/3 func (f *form) Parse(ctx *gin.Context, receiver interface{}) error { - + handleConfig := define.GetHttpHandleConfig() requestBody, _ := io.ReadAll(ctx.Request.Body) // 请求信息写入上下文 - ctx.Set(define.RecordRequestDataField, string(requestBody)) + ctx.Set(handleConfig.RecordRequestDataField, string(requestBody)) // 因为请求体被读一遍之后就没了,重新赋值 requestBody ctx.Request.Body = io.NopCloser(bytes.NewReader(requestBody)) method := strings.ToUpper(ctx.Request.Method) diff --git a/request/wrapper.go b/request/wrapper.go index 1cdc62a..67d6dd4 100644 --- a/request/wrapper.go +++ b/request/wrapper.go @@ -1,4 +1,4 @@ -// Package gin ... +// Package request ... // // Description : gin ... // @@ -8,9 +8,11 @@ package request import ( + "bytes" + "git.zhangdeman.cn/zhangdeman/consts" "git.zhangdeman.cn/zhangdeman/wrapper" "github.com/gin-gonic/gin" - "net/url" + "io" "strings" ) @@ -79,11 +81,19 @@ func (wh *wrapperHandle) GetScheme(ctx *gin.Context, defaultVal string) string { // Author : go_developer@163.com<白茶清欢> // // Date : 16:03 2024/1/2 -func (wh *wrapperHandle) GetQuery(ctx *gin.Context) url.Values { +func (wh *wrapperHandle) GetQuery(ctx *gin.Context) map[string]string { + query := make(map[string]string) if nil != ctx && nil != ctx.Request && nil != ctx.Request.URL { - return ctx.Request.URL.Query() + for paramName, valueList := range ctx.Request.URL.Query() { + if len(valueList) == 0 { + query[paramName] = "" + } else { + query[paramName] = valueList[0] + } + } + return query } - return make(url.Values) + return query } // GetMethod 获取请求方法 @@ -111,11 +121,124 @@ func (wh *wrapperHandle) GetContentType(ctx *gin.Context, defaultVal string) str return wrapper.TernaryOperator.String(len(contentType) > 0, wrapper.String(contentType), wrapper.String(defaultVal)).Value() } +// GetRequestBody 获取请求body +// +// Author : go_developer@163.com<白茶清欢> +// +// Date : 11:25 2024/7/26 +func (wh *wrapperHandle) GetRequestBody(ctx *gin.Context) map[string]any { + body := map[string]any{} + contentType := wh.GetContentType(ctx, "") + if strings.Contains(contentType, consts.MimeTypeXWWWFormUrlencoded) { // form请求 + if err := ctx.Request.ParseForm(); nil != err { + return body + } + for paramName, itemParam := range ctx.Request.PostForm { + if len(itemParam) > 0 { + body[paramName] = itemParam[0] + } else { + body[paramName] = "" + } + } + return body + } + + if strings.Contains(contentType, consts.MimeTypeJson) || nil != ctx.Request.Body { // json请求 或者非 json请求 存在 body + data, err := io.ReadAll(ctx.Request.Body) + if nil != err { + return body + } + ctx.Request.Body = io.NopCloser(bytes.NewBuffer(data)) + return body + } + + return body +} + // GetResponseBody 获取响应body // // Author : go_developer@163.com<白茶清欢> // // Date : 15:18 2024/1/2 -func (wh *wrapperHandle) GetResponseBody(ctx *gin.Context, defaultVal string) string { - return "" +func (wh *wrapperHandle) GetResponseBody(ctx *gin.Context, key string, defaultVal any) any { + if nil == ctx { + return defaultVal + } + if val, exist := ctx.Get(key); !exist || nil == val { + return defaultVal + } else { + return val + } +} + +// GetClientIp 获取请求客户端IP +// +// Author : go_developer@163.com<白茶清欢> +// +// Date : 16:31 2024/7/23 +func (wh *wrapperHandle) GetClientIp(ctx *gin.Context, defaultVal string) string { + if nil == ctx { + return defaultVal + } + return ctx.ClientIP() +} + +// GetUserAgent 获取user_agent +// +// Author : go_developer@163.com<白茶清欢> +// +// Date : 16:32 2024/7/23 +func (wh *wrapperHandle) GetUserAgent(ctx *gin.Context, defaultVal string) string { + if nil == ctx { + return defaultVal + } + return ctx.Request.UserAgent() +} + +// GetCtxData 获取请求上下文数据 +// +// Author : go_developer@163.com<白茶清欢> +// +// Date : 16:35 2024/7/23 +func (wh *wrapperHandle) GetCtxData(ctx *gin.Context, key string, defaultVal any) any { + if nil == ctx { + return defaultVal + } + if val, exist := ctx.Get(key); !exist || nil == val { + return defaultVal + } else { + return val + } +} + +// GetCtxStringData 获取字符串数据 +// +// Author : go_developer@163.com<白茶清欢> +// +// Date : 16:37 2024/7/23 +func (wh *wrapperHandle) GetCtxStringData(ctx *gin.Context, key string, defaultVal string) string { + if nil == ctx { + return defaultVal + } + val := ctx.GetString(key) + if len(val) == 0 { + return defaultVal + } + return val +} + +// GetCtxIntData 获取int数据 +// +// Author : go_developer@163.com<白茶清欢> +// +// Date : 16:39 2024/7/23 +func (wh *wrapperHandle) GetCtxIntData(ctx *gin.Context, key string, defaultVal int64) int64 { + if nil == ctx { + return defaultVal + } + val := wh.GetCtxData(ctx, key, nil) + if nil == val { + return defaultVal + } + return ctx.GetInt64(key) } diff --git a/response/response.go b/response/response.go index e8b35b9..8eda65e 100644 --- a/response/response.go +++ b/response/response.go @@ -43,18 +43,18 @@ func Send(ctx *gin.Context, code interface{}, httpCode int, data interface{}) { } // 设置数据已发送的标识 defer ctx.Set(hasSendResponseFlag, true) - finishRequestTime := time.Now() + responseConfig := define.GetHttpHandleConfig() + finishRequestTime := time.Now().UnixMilli() responseData := map[string]interface{}{ - define.ResponseCodeField: code, - define.ResponseMessageField: exception.GetMessage(code), - define.ResponseTraceIDField: ctx.GetString(define.TraceIDField), - define.ResponseRequestIDField: ctx.GetString(define.RequestIDField), - define.ResponseDataField: data, - define.HandleRequestCostField: finishRequestTime.UnixMilli() - ctx.GetTime(define.StartRequestTimeField).UnixMilli(), + responseConfig.ResponseCodeField: code, + responseConfig.ResponseMessageField: exception.GetMessage(code), + responseConfig.ResponseTraceIDField: ctx.GetString(responseConfig.ResponseTraceIDField), + responseConfig.ResponseDataField: data, + responseConfig.HandleRequestCostField: finishRequestTime - ctx.GetTime(responseConfig.StartRequestTimeField).UnixMilli(), } // 记录完成时间 - ctx.Set(define.FinishRequestTimeField, finishRequestTime) - ctx.Set(define.RecordResponseDataField, responseData) + ctx.Set(responseConfig.FinishRequestTimeField, finishRequestTime) + ctx.Set(responseConfig.ResponseDataField, responseData) responseException := exception.New(code, httpCode, responseData) ctx.JSON(responseException.GetHttpCode(), responseException.GetData()) }