You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
56 lines
1.3 KiB
56 lines
1.3 KiB
package jwt
|
|
|
|
import (
|
|
"embed"
|
|
"errors"
|
|
"fmt"
|
|
"github.com/dgrijalva/jwt-go"
|
|
)
|
|
|
|
// TokenData 用于存储解析的 token 数据
|
|
type TokenData struct {
|
|
Expired float64
|
|
Frequency float64
|
|
}
|
|
|
|
//go:embed server_public_key.pem
|
|
var publicKeyEmbed embed.FS
|
|
|
|
// VerifyToken 解析并验证 JWT,返回 TokenData 或错误
|
|
func VerifyToken(tokenString string) (*TokenData, error) {
|
|
// 从文件中读取公钥
|
|
publicKeyPem, err := publicKeyEmbed.ReadFile("server_public_key.pem")
|
|
if err != nil {
|
|
return nil, fmt.Errorf("加载公钥失败: %v", err)
|
|
}
|
|
|
|
publicKey, err := jwt.ParseRSAPublicKeyFromPEM(publicKeyPem)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("解析公钥失败: %v", err)
|
|
}
|
|
|
|
// 解析并验证 JWT
|
|
token, err := jwt.Parse(tokenString, func(token *jwt.Token) (interface{}, error) {
|
|
return publicKey, nil
|
|
})
|
|
|
|
if err != nil {
|
|
return nil, fmt.Errorf("令牌解析失败: %v", err)
|
|
}
|
|
|
|
if claims, ok := token.Claims.(jwt.MapClaims); ok && token.Valid {
|
|
expired, okExp := claims["expired"].(float64)
|
|
frequency, okFreq := claims["frequency"].(float64)
|
|
|
|
if !okExp || !okFreq {
|
|
return nil, errors.New("无效的令牌负载")
|
|
}
|
|
|
|
return &TokenData{
|
|
Expired: expired,
|
|
Frequency: frequency,
|
|
}, nil
|
|
} else {
|
|
return nil, errors.New("无效令牌")
|
|
}
|
|
}
|
|
|