This commit is contained in:
wwweww
2026-02-23 20:36:21 +08:00
parent 4898aecd3b
commit fdbcde13b2
52 changed files with 11263 additions and 194 deletions
+90
View File
@@ -0,0 +1,90 @@
package utils
import (
"encoding/base64"
"encoding/json"
"fmt"
"time"
"github.com/golang-jwt/jwt/v4"
)
// JWKS (JSON Web Key Set) 结构
type JWKSKey struct {
Kty string `json:"kty"`
Use string `json:"use"`
Kid string `json:"kid"`
N string `json:"n,omitempty"`
E string `json:"e,omitempty"`
K string `json:"k,omitempty"` // 对称密钥
Alg string `json:"alg"`
}
type JWKS struct {
Keys []JWKSKey `json:"keys"`
}
// GenerateJWKSFromSecret 从密钥生成 JWKS(用于对称加密 HS256)
func GenerateJWKSFromSecret(secretKey string, keyID string) *JWKS {
// 对于 HS256,将密钥进行 base64 编码
encodedSecret := base64.RawURLEncoding.EncodeToString([]byte(secretKey))
return &JWKS{
Keys: []JWKSKey{
{
Kty: "oct",
Use: "sig",
Kid: keyID,
K: encodedSecret,
Alg: "HS256",
},
},
}
}
// GenerateJWKSEndpoint 生成可以被 Envoy 使用的 JWKS JSON
// 此端点应在 user-rpc 中暴露,URL 为 /.well-known/jwks.json
func GenerateJWKSEndpoint(secretKey string, keyID string) (string, error) {
if secretKey == "" {
return "", fmt.Errorf("secret key cannot be empty")
}
jwks := GenerateJWKSFromSecret(secretKey, keyID)
jsonData, err := json.MarshalIndent(jwks, "", " ")
if err != nil {
return "", err
}
return string(jsonData), nil
}
// TokenPayload 令牌负载
type TokenMetadata struct {
IssuedAt time.Time
ExpiresAt time.Time
Subject string // userId
Issuer string
Audience string
}
// ExtractTokenMetadata 从 token 中提取元数据(不验证签名)
func ExtractTokenMetadata(tokenString string) (*TokenMetadata, error) {
token, _, err := new(jwt.Parser).ParseUnverified(tokenString, &Claims{})
if err != nil {
return nil, err
}
claims, ok := token.Claims.(*Claims)
if !ok {
return nil, fmt.Errorf("invalid token claims type")
}
return &TokenMetadata{
IssuedAt: claims.IssuedAt.Time,
ExpiresAt: claims.ExpiresAt.Time,
Subject: claims.UserId,
Issuer: claims.Issuer,
Audience: "", // 如果需要,可以增加到 Claims 中
}, nil
}