Files
2026-08-15 17:04:47 +08:00

68 lines
1.8 KiB
Go
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
package commonservice
import (
"time"
"github.com/golang-jwt/jwt/v5"
)
// Claims 是 access / refresh token 的载荷。
type Claims struct {
UserID int64 `json:"userId"`
Username string `json:"username"`
Type string `json:"type"` // access | refresh
jwt.RegisteredClaims
}
// IssueAccess 签发 access token。
func IssueAccess(secret string, userID int64, username string, ttlHours int) (string, error) {
if ttlHours <= 0 {
ttlHours = 2
}
return issue(secret, userID, username, "access", time.Duration(ttlHours)*time.Hour)
}
// IssueRefresh 签发 refresh token。
func IssueRefresh(secret string, userID int64, username string, ttlDays int) (string, error) {
if ttlDays <= 0 {
ttlDays = 30
}
return issue(secret, userID, username, "refresh", time.Duration(ttlDays)*24*time.Hour)
}
func issue(secret string, userID int64, username, typ string, ttl time.Duration) (string, error) {
now := time.Now()
claims := Claims{
UserID: userID,
Username: username,
Type: typ,
RegisteredClaims: jwt.RegisteredClaims{
IssuedAt: jwt.NewNumericDate(now),
ExpiresAt: jwt.NewNumericDate(now.Add(ttl)),
},
}
t := jwt.NewWithClaims(jwt.SigningMethodHS256, claims)
return t.SignedString([]byte(secret))
}
// Parse 校验并解析 JWTtyp 非空时要求 claims.Type 匹配。
func Parse(secret, token, typ string) (*Claims, error) {
parsed, err := jwt.ParseWithClaims(token, &Claims{}, func(t *jwt.Token) (any, error) {
if t.Method != jwt.SigningMethodHS256 {
return nil, Unauthorized("UNAUTHORIZED")
}
return []byte(secret), nil
})
if err != nil || !parsed.Valid {
return nil, Unauthorized("UNAUTHORIZED")
}
claims, ok := parsed.Claims.(*Claims)
if !ok || claims.UserID <= 0 {
return nil, Unauthorized("UNAUTHORIZED")
}
if typ != "" && claims.Type != typ {
return nil, Unauthorized("UNAUTHORIZED")
}
return claims, nil
}