Quellcode durchsuchen

调用mcp-调用工具测试通过

qdy vor 1 Monat
Ursprung
Commit
3db62886e0

+ 68
- 0
authbase/basic_auth_middewara.go Datei anzeigen

@@ -8,55 +8,106 @@ import (
8 8
 
9 9
 	"git.x2erp.com/qdy/go-base/config"
10 10
 	"git.x2erp.com/qdy/go-base/ctx"
11
+	"git.x2erp.com/qdy/go-base/logger"
11 12
 )
12 13
 
13 14
 // BasicAuth 简化的Basic认证中间件
14 15
 func BasicAuth(next http.Handler) http.Handler {
15 16
 	return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
17
+		if logger.IsDebug() {
18
+			logger.Debug("BasicAuth中间件开始处理请求: %s %s", r.Method, r.URL.Path)
19
+		}
16 20
 		// 1. 检查认证头
17 21
 		authHeader := r.Header.Get("Authorization")
18 22
 		if authHeader == "" {
23
+			if logger.IsDebug() {
24
+				logger.Debug("认证头缺失,请求未授权: %s %s", r.Method, r.URL.Path)
25
+			}
19 26
 			unauthorized(w, "缺少认证信息")
20 27
 			return
21 28
 		}
22 29
 
30
+		if logger.IsDebug() {
31
+			displayHeader := authHeader
32
+			if len(displayHeader) > 20 {
33
+				displayHeader = displayHeader[:20] + "..."
34
+			}
35
+			logger.Debug("收到认证头: %s", displayHeader)
36
+		}
37
+
23 38
 		// 2. 检查Basic格式
24 39
 		if !strings.HasPrefix(authHeader, "Basic ") {
40
+			if logger.IsDebug() {
41
+				displayHeader := authHeader
42
+				if len(displayHeader) > 20 {
43
+					displayHeader = displayHeader[:20] + "..."
44
+				}
45
+				logger.Debug("认证格式错误,需要Basic认证: %s", displayHeader)
46
+			}
25 47
 			unauthorized(w, "认证格式错误,请使用Basic认证")
26 48
 			return
27 49
 		}
28 50
 
29 51
 		// 3. 解码凭证
30 52
 		base64Creds := strings.TrimPrefix(authHeader, "Basic ")
53
+		if logger.IsDebug() {
54
+			logger.Debug("解码Base64凭证,长度: %d", len(base64Creds))
55
+		}
31 56
 		credsBytes, err := base64.StdEncoding.DecodeString(base64Creds)
32 57
 		if err != nil {
58
+			if logger.IsDebug() {
59
+				logger.Debug("Base64解码失败: %v", err)
60
+			}
33 61
 			unauthorized(w, "认证信息解码失败")
34 62
 			return
35 63
 		}
36 64
 
37 65
 		// 4. 分割用户名密码
38 66
 		creds := string(credsBytes)
67
+		if logger.IsDebug() {
68
+			logger.Debug("解码后凭证长度: %d", len(creds))
69
+		}
39 70
 		parts := strings.SplitN(creds, ":", 2)
40 71
 		if len(parts) != 2 {
72
+			if logger.IsDebug() {
73
+				logger.Debug("用户名密码格式错误,分割后部分数: %d", len(parts))
74
+			}
41 75
 			unauthorized(w, "用户名密码格式错误")
42 76
 			return
43 77
 		}
44 78
 
45 79
 		username := parts[0]
46 80
 		password := parts[1]
81
+		if logger.IsDebug() {
82
+			logger.Debug("提取用户名: %s,密码长度: %d", username, len(password))
83
+		}
47 84
 
48 85
 		// 5. 验证用户名密码
86
+		if logger.IsDebug() {
87
+			logger.Debug("开始验证用户名密码: %s", username)
88
+		}
49 89
 		userID, tenantID, ok := verifyCredentials(username, password)
50 90
 		if !ok {
91
+			if logger.IsDebug() {
92
+				logger.Debug("用户名密码验证失败: %s", username)
93
+			}
51 94
 			unauthorized(w, "用户名或密码错误")
52 95
 			return
53 96
 		}
97
+		if logger.IsDebug() {
98
+			logger.Debug("用户名密码验证成功: userID=%s, tenantID=%s", userID, tenantID)
99
+		}
54 100
 
55 101
 		// 6. 创建请求上下文
56 102
 		traceID := r.Header.Get("X-Trace-ID")
57 103
 		if traceID == "" {
58 104
 			// 生成简单的时间戳追踪ID
59 105
 			traceID = time.Now().Format("20060102150405.000")
106
+			if logger.IsDebug() {
107
+				logger.Debug("生成TraceID: %s", traceID)
108
+			}
109
+		} else if logger.IsDebug() {
110
+			logger.Debug("使用请求中的TraceID: %s", traceID)
60 111
 		}
61 112
 
62 113
 		cfg := config.GetConfig()
@@ -70,16 +121,27 @@ func BasicAuth(next http.Handler) http.Handler {
70 121
 			Username:     username,
71 122
 		}
72 123
 
124
+		if logger.IsDebug() {
125
+			logger.Debug("创建请求上下文: service=%s, instance=%s, tenant=%s, user=%s",
126
+				requestCtx.ServiceName, requestCtx.InstanceName, requestCtx.TenantID, requestCtx.UserID)
127
+		}
128
+
73 129
 		// 7. 保存到请求
74 130
 		r = ctx.SaveContext(r, requestCtx)
75 131
 
76 132
 		// 8. 继续处理
133
+		if logger.IsDebug() {
134
+			logger.Debug("BasicAuth中间件处理完成,继续下一个处理器")
135
+		}
77 136
 		next.ServeHTTP(w, r)
78 137
 	})
79 138
 }
80 139
 
81 140
 // 验证用户名密码(简单示例)
82 141
 func verifyCredentials(username, password string) (userID, tenantID string, ok bool) {
142
+	if logger.IsDebug() {
143
+		logger.Debug("验证凭据,用户名: %s", username)
144
+	}
83 145
 
84 146
 	// 这里替换为你的实际验证逻辑
85 147
 	cfg := config.GetConfig()
@@ -87,7 +149,13 @@ func verifyCredentials(username, password string) (userID, tenantID string, ok b
87 149
 	sysPassword := cfg.GetServiceConfig().Password
88 150
 
89 151
 	if username == sysUsername && password == sysPassword {
152
+		if logger.IsDebug() {
153
+			logger.Debug("凭据验证成功,用户名匹配系统用户")
154
+		}
90 155
 		return sysUsername, "tenant-admin", true
91 156
 	}
157
+	if logger.IsDebug() {
158
+		logger.Debug("凭据验证失败,用户名或密码不匹配")
159
+	}
92 160
 	return "", "", false
93 161
 }

+ 125
- 3
authbase/token_auth_middleware.go Datei anzeigen

@@ -8,33 +8,64 @@ import (
8 8
 
9 9
 	"git.x2erp.com/qdy/go-base/config"
10 10
 	"git.x2erp.com/qdy/go-base/ctx"
11
+	"git.x2erp.com/qdy/go-base/logger"
11 12
 	"git.x2erp.com/qdy/go-base/util/jwt"
12 13
 )
13 14
 
14 15
 // TokenAuth 简化的Bearer认证中间件
15 16
 func TokenAuth(next http.Handler) http.Handler {
16 17
 	return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
18
+		if logger.IsDebug() {
19
+			logger.Debug("TokenAuth中间件开始处理请求: %s %s", r.Method, r.URL.Path)
20
+		}
17 21
 		// 1. 检查认证头
18 22
 		authHeader := r.Header.Get("Authorization")
19 23
 		if authHeader == "" {
24
+			if logger.IsDebug() {
25
+				logger.Debug("认证头缺失,请求未授权: %s %s", r.Method, r.URL.Path)
26
+			}
20 27
 			unauthorized(w, "缺少认证信息")
21 28
 			return
22 29
 		}
23 30
 
24
-		// 2. 检查Basic格式
31
+		if logger.IsDebug() {
32
+			displayHeader := authHeader
33
+			if len(displayHeader) > 20 {
34
+				displayHeader = displayHeader[:20] + "..."
35
+			}
36
+			logger.Debug("收到认证头: %s", displayHeader)
37
+		}
38
+
39
+		// 2. 检查Bearer格式
25 40
 		if !strings.HasPrefix(authHeader, "Bearer ") {
41
+			if logger.IsDebug() {
42
+				displayHeader := authHeader
43
+				if len(displayHeader) > 20 {
44
+					displayHeader = displayHeader[:20] + "..."
45
+				}
46
+				logger.Debug("认证格式错误,需要Bearer认证: %s", displayHeader)
47
+			}
26 48
 			unauthorized(w, "认证格式错误,请使用Bearer认证")
27 49
 			return
28 50
 		}
29 51
 
30 52
 		// 3. 解码凭证
31 53
 		token := strings.TrimPrefix(authHeader, "Bearer ")
54
+		if logger.IsDebug() {
55
+			logger.Debug("验证JWT令牌,令牌长度: %d", len(token))
56
+		}
32 57
 
33 58
 		// 验证JWT令牌
34 59
 		claims, err := validToken(token)
35 60
 		if err != nil {
36
-
61
+			if logger.IsDebug() {
62
+				logger.Debug("JWT令牌验证失败: %v", err)
63
+			}
37 64
 			unauthorized(w, fmt.Sprintf("Invalid token: %v", err))
65
+			return
66
+		}
67
+		if logger.IsDebug() {
68
+			logger.Debug("JWT令牌验证成功,用户: %s, 租户: %s", claims.Username, claims.TenantID)
38 69
 		}
39 70
 
40 71
 		// 6. 创建请求上下文
@@ -42,6 +73,11 @@ func TokenAuth(next http.Handler) http.Handler {
42 73
 		if traceID == "" {
43 74
 			// 生成简单的时间戳追踪ID
44 75
 			traceID = time.Now().Format("20060102150405.000")
76
+			if logger.IsDebug() {
77
+				logger.Debug("生成TraceID: %s", traceID)
78
+			}
79
+		} else if logger.IsDebug() {
80
+			logger.Debug("使用请求中的TraceID: %s", traceID)
45 81
 		}
46 82
 
47 83
 		cfg := config.GetConfig()
@@ -56,10 +92,18 @@ func TokenAuth(next http.Handler) http.Handler {
56 92
 			ProjectID:    claims.ProjectID,
57 93
 		}
58 94
 
95
+		if logger.IsDebug() {
96
+			logger.Debug("创建请求上下文: service=%s, instance=%s, tenant=%s, user=%s",
97
+				requestCtx.ServiceName, requestCtx.InstanceName, requestCtx.TenantID, requestCtx.UserID)
98
+		}
99
+
59 100
 		// 7. 保存到请求
60 101
 		r = ctx.SaveContext(r, requestCtx)
61 102
 
62 103
 		// 8. 继续处理
104
+		if logger.IsDebug() {
105
+			logger.Debug("TokenAuth中间件处理完成,继续下一个处理器")
106
+		}
63 107
 		next.ServeHTTP(w, r)
64 108
 	})
65 109
 }
@@ -67,6 +111,84 @@ func TokenAuth(next http.Handler) http.Handler {
67 111
 // 验证令牌(需要根据实际项目实现)
68 112
 func validToken(token string) (*jwt.Claims, error) {
69 113
 	secretKey := config.GetServiceConfig().SecretKey
70
-	//logger.Debug("secretKey:%s", secretKey)
114
+	if logger.IsDebug() {
115
+		logger.Debug("验证JWT令牌,secretKey长度: %d", len(secretKey))
116
+	}
71 117
 	return jwt.ParseToken(token, secretKey)
72 118
 }
119
+
120
+// PrintAllHeaders 打印HTTP请求的所有头部信息
121
+// func printAllHeaders(r *http.Request) {
122
+// 	if !logger.IsDebug() {
123
+// 		return
124
+// 	}
125
+// 	logger.Debug("=== HTTP 请求头 ===")
126
+// 	for name, values := range r.Header {
127
+// 		for _, value := range values {
128
+// 			logger.Debug("%s: %s", name, value)
129
+// 		}
130
+// 	}
131
+// 	logger.Debug("==================")
132
+// }
133
+
134
+// DebugPrintFullRequest 打印完整的HTTP请求信息(头+体),并确保请求体可被后续代码正常读取。
135
+// 将此函数在处理请求的最开始调用。
136
+// func debugPrintFullRequest(r *http.Request) {
137
+// 	if !logger.IsDebug() {
138
+// 		return
139
+// 	}
140
+// 	logger.Debug("🔍 [DEBUG] ====== 开始打印完整请求 ======")
141
+
142
+// 	// 1. 打印基本请求信息
143
+// 	logger.Debug("[DEBUG] 方法: %s, URL: %s, 协议: %s", r.Method, r.URL.String(), r.Proto)
144
+
145
+// 	// 2. 打印所有请求头
146
+// 	logger.Debug("[DEBUG] --- 请求头 ---")
147
+// 	// 按字母顺序排序输出,更易读
148
+// 	var headers []string
149
+// 	for key := range r.Header {
150
+// 		headers = append(headers, key)
151
+// 	}
152
+// 	sort.Strings(headers)
153
+// 	for _, key := range headers {
154
+// 		logger.Debug("[DEBUG] %s: %s", key, strings.Join(r.Header[key], ", "))
155
+// 	}
156
+
157
+// 	// 3. 【核心】读取、打印并恢复请求体
158
+// 	logger.Debug("[DEBUG] --- 请求体 (原始) ---")
159
+// 	if r.Body == nil || r.ContentLength == 0 {
160
+// 		logger.Debug("[DEBUG] 请求体为空")
161
+// 	} else {
162
+// 		// 读取原始Body内容
163
+// 		originalBodyBytes, err := io.ReadAll(r.Body)
164
+// 		if err != nil {
165
+// 			logger.Debug("[DEBUG] 读取请求体失败: %v", err)
166
+// 			// 即使失败,也要尝试恢复一个空Body,避免后续panic
167
+// 			r.Body = io.NopCloser(bytes.NewBuffer(nil))
168
+// 			return
169
+// 		}
170
+// 		// 重要:立即关闭原Body流
171
+// 		r.Body.Close()
172
+
173
+// 		// 打印原始内容
174
+// 		logger.Debug("[DEBUG] 内容长度: %d 字节", len(originalBodyBytes))
175
+// 		logger.Debug(string(originalBodyBytes))
176
+
177
+// 		// 【关键步骤】将读取的字节重新设置回 r.Body,供后续使用
178
+// 		r.Body = io.NopCloser(bytes.NewBuffer(originalBodyBytes))
179
+
180
+// 		// 4. (可选)尝试美化打印JSON,便于阅读
181
+// 		logger.Debug("[DEBUG] --- 请求体 (JSON美化) ---")
182
+// 		if len(originalBodyBytes) > 0 {
183
+// 			var prettyJSON bytes.Buffer
184
+// 			if err := json.Indent(&prettyJSON, originalBodyBytes, "", "  "); err == nil {
185
+// 				// 是有效的JSON
186
+// 				logger.Debug(prettyJSON.String())
187
+// 			} else {
188
+// 				// 不是JSON或格式错误,打印原始内容
189
+// 				logger.Debug("[DEBUG] 内容非JSON格式,上方已打印原始内容。")
190
+// 			}
191
+// 		}
192
+// 	}
193
+// 	logger.Debug("🔍 [DEBUG] ====== 结束打印 ======\n")
194
+// }

+ 1
- 3
config/subconfigs/database_common.go Datei anzeigen

@@ -20,9 +20,7 @@ type DbConfig struct {
20 20
 
21 21
 // SetDbDefaults 设置数据库配置默认值
22 22
 func SetDbDefaults(c *DbConfig) {
23
-	if c.Type == "" {
24
-		c.Type = "mysql"
25
-	}
23
+
26 24
 	if c.Port == 0 {
27 25
 		c.Port = 3306
28 26
 	}

+ 5
- 1
config/subconfigs/database_config.go Datei anzeigen

@@ -1,6 +1,8 @@
1 1
 package subconfigs
2 2
 
3
-import "git.x2erp.com/qdy/go-base/config/core"
3
+import (
4
+	"git.x2erp.com/qdy/go-base/config/core"
5
+)
4 6
 
5 7
 // DatabaseConfig 单个数据库配置
6 8
 type DatabaseConfig struct {
@@ -18,7 +20,9 @@ func (c *DatabaseConfig) SetDefaults() {
18 20
 }
19 21
 
20 22
 func (c *DatabaseConfig) Load(data map[string]interface{}) error {
23
+
21 24
 	return c.LoadFromYAML(data, c)
25
+
22 26
 }
23 27
 
24 28
 func (c *DatabaseConfig) Validate() error {

Laden…
Abbrechen
Speichern