Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent) Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
77 lines
2.2 KiB
Go
77 lines
2.2 KiB
Go
package auth
|
||
|
||
import (
|
||
"fmt"
|
||
"time"
|
||
|
||
"github.com/golang-jwt/jwt/v5"
|
||
)
|
||
|
||
// PersonalCustomerClaims 个人客户 JWT Claims
|
||
type PersonalCustomerClaims struct {
|
||
CustomerID uint `json:"customer_id"` // 个人客户 ID
|
||
Phone string `json:"phone"` // 手机号
|
||
AssetType string `json:"asset_type"` // 登录所用资产类型(iot_card / device)
|
||
AssetID uint `json:"asset_id"` // 登录所用资产 ID
|
||
jwt.RegisteredClaims
|
||
}
|
||
|
||
// JWTManager JWT 管理器
|
||
type JWTManager struct {
|
||
secretKey string
|
||
tokenDuration time.Duration
|
||
}
|
||
|
||
// NewJWTManager 创建 JWT 管理器
|
||
func NewJWTManager(secretKey string, tokenDuration time.Duration) *JWTManager {
|
||
return &JWTManager{
|
||
secretKey: secretKey,
|
||
tokenDuration: tokenDuration,
|
||
}
|
||
}
|
||
|
||
// GeneratePersonalCustomerToken 生成个人客户 Token
|
||
func (m *JWTManager) GeneratePersonalCustomerToken(customerID uint, phone string, assetType string, assetID uint) (string, error) {
|
||
claims := &PersonalCustomerClaims{
|
||
CustomerID: customerID,
|
||
Phone: phone,
|
||
AssetType: assetType,
|
||
AssetID: assetID,
|
||
RegisteredClaims: jwt.RegisteredClaims{
|
||
ExpiresAt: jwt.NewNumericDate(time.Now().Add(m.tokenDuration)),
|
||
IssuedAt: jwt.NewNumericDate(time.Now()),
|
||
NotBefore: jwt.NewNumericDate(time.Now()),
|
||
},
|
||
}
|
||
|
||
token := jwt.NewWithClaims(jwt.SigningMethodHS256, claims)
|
||
tokenString, err := token.SignedString([]byte(m.secretKey))
|
||
if err != nil {
|
||
return "", fmt.Errorf("生成 Token 失败: %w", err)
|
||
}
|
||
|
||
return tokenString, nil
|
||
}
|
||
|
||
// VerifyPersonalCustomerToken 验证个人客户 Token
|
||
func (m *JWTManager) VerifyPersonalCustomerToken(tokenString string) (*PersonalCustomerClaims, error) {
|
||
token, err := jwt.ParseWithClaims(tokenString, &PersonalCustomerClaims{}, func(token *jwt.Token) (interface{}, error) {
|
||
// 验证签名算法
|
||
if _, ok := token.Method.(*jwt.SigningMethodHMAC); !ok {
|
||
return nil, fmt.Errorf("unexpected signing method: %v", token.Header["alg"])
|
||
}
|
||
return []byte(m.secretKey), nil
|
||
})
|
||
|
||
if err != nil {
|
||
return nil, fmt.Errorf("Token 解析失败: %w", err)
|
||
}
|
||
|
||
claims, ok := token.Claims.(*PersonalCustomerClaims)
|
||
if !ok || !token.Valid {
|
||
return nil, fmt.Errorf("Token 无效")
|
||
}
|
||
|
||
return claims, nil
|
||
}
|