gtoken

package module
v0.0.2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jul 6, 2026 License: MIT Imports: 16 Imported by: 0

README

gtoken

基于 GoFrame v2 框架的轻量级 Token 认证插件,提供登录、登出、token 续期等功能。

特性

  • 支持多种缓存模式(gcache / gredis)
  • 支持多种 Token 生成方式(UUID / 随机字符串)
  • 单点登录与多端登录模式
  • Token 自动续期机制
  • HTTP Middleware 集成
  • 排除路径配置

安装

go get github.com/lonevle/gtoken

快速开始

方式一:代码配置
package main

import (
    "github.com/gogf/gf/v2/frame/g"
    "github.com/gogf/gf/v2/net/ghttp"
    "github.com/lonevle/gtoken"
)

func main() {
    s := g.Server()
    
    // 初始化 gtoken
    gtoken.Init(&gtoken.Config{
        CacheMode:        gtoken.CacheModeCache, // 缓存模式:1 gcache 2 gredis
        CachePreKey:      "gtoken_",             // 缓存 key 前缀
        TokenStyle:       gtoken.TokenStyleUUID, // Token 风格
        TokenExpire:      2 * time.Hour,         // Token 过期时间
        MultiLogin:       false,                 // 是否支持多端登录
        EnableRenew:      true,                  // 是否开启续期
        RenewThreshold:   30 * time.Minute,      // 续期阈值
        AuthExcludePaths: []string{"/login"},    // 排除路径
        AuthHeaderName:   "Authorization",       // 认证 header 名称
        TokenPrefix:      "Bearer ",             // Token 前缀
    })
    
    // 注册中间件
    s.Group("/", func(group *ghttp.RouterGroup) {
        group.Middleware(gtoken.NewMiddleware().Auth)
        group.GET("/login", loginHandler)
        group.GET("/logout", logoutHandler)
        group.GET("/user", userHandler)
    })
    
    s.Run()
}

func loginHandler(r *ghttp.Request) {
    token, err := gtoken.Login(r.Context(), "user001")
    if err != nil {
        r.Response.WriteJsonExit(map[string]any{"code": 1, "msg": err.Error()})
    }
    r.Response.WriteJsonExit(map[string]any{"code": 0, "token": token})
}

func logoutHandler(r *ghttp.Request) {
    err := gtoken.Logout(r.Context(), "user001")
    if err != nil {
        r.Response.WriteJsonExit(map[string]any{"code": 1, "msg": err.Error()})
    }
    r.Response.WriteJsonExit(map[string]any{"code": 0, "msg": "success"})
}

func userHandler(r *ghttp.Request) {
    userID := r.GetCtxVar("userID").String()
    r.Response.WriteJsonExit(map[string]any{"code": 0, "userID": userID})
}
方式二:配置文件

config.yaml 中配置:

gToken:
  cacheMode: 1              # 缓存模式:1 gcache 2 gredis
  cachePreKey: "gtoken_"    # 缓存 key 前缀
  tokenStyle: "uuid"        # Token 风格:uuid / rand64 / rand128
  tokenExpire: "2h"         # Token 过期时间,默认 2h(支持格式:2h, 30m, 7200s)
  multiLogin: false         # 是否支持多端登录
  enableRenew: true         # 是否开启续期,默认 false
  renewThreshold: "30m"     # 续期阈值,默认 30m(支持格式:30m, 1800s)
  renewTimeout: "3s"        # 续期超时时间,默认 3s
  authExcludePaths:         # 排除路径
    - /login
    - /register
  authHeaderName: "Authorization"  # 认证 header 名称
  tokenPrefix: "Bearer "           # Token 前缀

然后在代码中加载:

func main() {
    config := gtoken.NewConfigFromCtx(gctx.New())
    gtoken.Init(config)
    // ...
}

配置说明

字段 类型 默认值 说明
CacheMode int8 1 缓存模式:1 gcache(内存),2 gredis(Redis)
CachePreKey string gtoken_ 缓存 key 前缀
TokenStyle string uuid Token 风格:uuidrand64rand128
TokenExpire time.Duration 2小时 Token 过期时间
MultiLogin bool false 是否支持多端登录,true 允许多端,false 单点登录
EnableRenew bool false 是否开启续期模式
RenewThreshold time.Duration 30分钟 续期阈值,需小于 TokenExpire
RenewTimeout time.Duration 3秒 续期操作超时时间
AuthExcludePaths []string nil 认证排除路径,如 /login
AuthHeaderName string Authorization 认证 header 名称
TokenPrefix string `` Token 前缀,如 Bearer

API 方法

包级函数使用方式(推荐):

登录
token, err := gtoken.Login(ctx, userID string) (string, error)
登出
err := gtoken.Logout(ctx, userID string) error
通过 Token 登出
err := gtoken.LogoutByToken(ctx, token string) error
验证登录状态
userID, isLoggedIn, err := gtoken.IsLogin(ctx, token string) (*gvar.Var, bool, error)
通过 Token 获取用户 ID
userID, err := gtoken.GetUserIDByToken(ctx, token string) (*gvar.Var, error)
通过用户 ID 获取 Token
token, err := gtoken.GetTokenByUserKey(ctx, userID string) (string, error)
生成 Token
token, err := gtoken.GenerateToken(userID string) (string, error)
路径管理
// 添加排除路径
gtoken.AddExcludePaths("/login", "/register")

// 检查路径是否在排除列表
exists := gtoken.SearchPath("/login")

// 移除排除路径
gtoken.RemovePaths("/login")

// 清空排除路径
gtoken.ClearPaths()

Middleware 使用

默认响应
group.Middleware(gtoken.NewMiddleware().Auth)

默认响应格式:

{
    "code": 40000,
    "message": "error message",
    "data": null
}
自定义响应
group.Middleware(gtoken.NewMiddleware(func(r *ghttp.Request, err error) {
    r.Response.WriteJsonExit(map[string]any{
        "code":    401,
        "message": "未登录或登录已过期",
    })
}).Auth)

Token 风格

风格 说明
TokenStyleUUID 使用 UUID 生成,32 字节,包含 MAC、PID、时间戳、序列号、随机数
TokenStyleRand64 使用随机字符串生成,64 字节
TokenStyleRand128 使用随机字符串生成,128 字节

缓存模式

模式 说明
CacheModeCache 使用 GoFrame 内置缓存(gcache),适用于单实例部署
CacheModeRedis 使用 Redis 缓存,适用于多实例部署(需要提前配置 Redis)

注意事项

  1. 分布式锁:当前使用 gmlock(进程内锁),在 Redis 多实例环境下无法提供分布式锁保护
  2. Token 续期EnableRenew 默认关闭(false),需显式开启
  3. 单点登录MultiLoginfalse 时,每次登录会生成新 Token 并失效旧 Token

Documentation

Index

Constants

View Source
const (
	CacheModeCache = 1
	CacheModeRedis = 2
)

缓存模式

View Source
const (
	UserKeyPrefix  = "account:"
	TokenKeyPrefix = "token:"
)

常量

View Source
const (
	MsgErrUserIDEmpty       = "userID empty"
	MsgErrDataEmpty         = "cache value is nil"
	MsgErrTokenEmpty        = "token empty"
	MsgErrExpiredOrNotExist = "Data Expired or not Exist"
	MsgErrInstanceNotInit   = "GToken instance not initialized"
)

错误信息

Variables

This section is empty.

Functions

func AddExcludePaths added in v0.0.2

func AddExcludePaths(urls ...string)

AddExcludePaths 添加认证排除路径,这些路径不需要 token 验证 urls: 需要排除的路径列表

func ClearPaths added in v0.0.2

func ClearPaths()

ClearPaths 清空所有排除路径

func GenerateToken added in v0.0.2

func GenerateToken(userID string) (string, error)

GenerateToken 生成新的 token userID: 用户唯一标识 return: token 和错误信息

func GetRequestToken

func GetRequestToken(r *ghttp.Request) (string, error)

func GetTokenByUserKey added in v0.0.2

func GetTokenByUserKey(ctx context.Context, userID string) (string, error)

GetTokenByUserKey 通过用户 ID 获取 token ctx: 上下文 userID: 用户唯一标识 return: token 和错误信息

func GetUserIDByToken added in v0.0.2

func GetUserIDByToken(ctx context.Context, token string) (*gvar.Var, error)

GetUserIDByToken 通过 token 获取用户 ID ctx: 上下文 token: 用户 token return: 用户 ID 和错误信息

func IsLogin added in v0.0.2

func IsLogin(ctx context.Context, token string) (userID *gvar.Var, isLoggedIn bool, err error)

IsLogin 验证 token 是否有效,判断用户是否已登录 ctx: 上下文 token: 用户 token return: 用户 ID、是否登录、错误信息

func Login added in v0.0.2

func Login(ctx context.Context, userID string) (string, error)

Login 用户登录,生成并返回 token ctx: 上下文 userID: 用户唯一标识 return: token 和错误信息

func Logout added in v0.0.2

func Logout(ctx context.Context, userID string) error

Logout 用户退出登录,清除用户相关的 token 缓存 ctx: 上下文 userID: 用户唯一标识 return: 错误信息

func LogoutByToken added in v0.0.2

func LogoutByToken(ctx context.Context, token string) error

LogoutByToken 通过 token 退出登录,清除该 token 及关联的用户缓存 ctx: 上下文 token: 用户 token return: 错误信息

func RemovePaths added in v0.0.2

func RemovePaths(urls ...string)

RemovePaths 移除排除路径 urls: 要移除的路径列表

func SearchPath added in v0.0.2

func SearchPath(url string) bool

SearchPath 检查路径是否在排除列表中 url: 要检查的路径 return: 是否在排除列表中

Types

type Config

type Config struct {
	CacheMode        int8          `c:"cacheMode"`        // 缓存模式 1 gcache 2 gredis 默认1
	CachePreKey      string        `c:"cachePreKey"`      // 缓存key前缀
	TokenStyle       TokenStyle    `c:"tokenStyle"`       // Token风格 默认 uuid
	TokenExpire      time.Duration `c:"tokenExpire"`      // Token过期时间 默认 2小时
	MultiLogin       bool          `c:"multiLogin"`       // 是否支持多端登录,默认false, (为true时支持多端登录,为false时仅允许一个端点登录)
	EnableRenew      bool          `c:"enableRenew"`      // 是否开启续期模式,默认false, (为true时在token过期前续期,为false时不续期)
	RenewThreshold   time.Duration `c:"renewThreshold"`   // 续期阈值,默认30分钟, 续签时间必须小于TokenExpire(距离过期时间多少开始续签)
	RenewTimeout     time.Duration `c:"renewTimeout"`     // 续期超时时间(默认3秒)
	AuthExcludePaths []string      `c:"authExcludePaths"` // 拦截排除地址 如: /login
	AuthHeaderName   string        `c:"authHeaderName"`   // 验证header的名称 默认 Authorization
	TokenPrefix      string        `c:"tokenPrefix"`      // token前缀 如`Bearer `
}

func NewConfigFromCtx

func NewConfigFromCtx(ctx context.Context) *Config

从配置文件中读取

type Manager

type Manager struct {
	// contains filtered or unexported fields
}
var (
	Instance *Manager
)

全局实例

func Init

func Init(config *Config) *Manager

初始化GToken实例

func (*Manager) AddExcludePaths

func (m *Manager) AddExcludePaths(urls ...string)

添加排除路径

func (*Manager) ClearPaths

func (m *Manager) ClearPaths()

清空排除路径

func (*Manager) GenerateToken

func (m *Manager) GenerateToken(userID string) (string, error)

生成token

func (*Manager) GetTokenByUserKey

func (m *Manager) GetTokenByUserKey(ctx context.Context, userID string) (string, error)

通过userID获取token, token过期或不存在error

func (*Manager) GetUserIDByToken

func (m *Manager) GetUserIDByToken(ctx context.Context, token string) (*gvar.Var, error)

通过token获取userID, UserID过期或不存在error

func (*Manager) IsLogin

func (m *Manager) IsLogin(ctx context.Context, token string) (userID *gvar.Var, isLoggedIn bool, err error)

func (*Manager) Login

func (m *Manager) Login(ctx context.Context, userID string) (string, error)

登录

func (*Manager) Logout

func (m *Manager) Logout(ctx context.Context, userID string) error

退出登录

func (*Manager) LogoutByToken

func (m *Manager) LogoutByToken(ctx context.Context, token string) error

通过token退出登录

func (*Manager) RemovePaths

func (m *Manager) RemovePaths(url ...string)

移除排除路径

func (*Manager) SearchPath

func (m *Manager) SearchPath(url string) bool

检查是否包含该路径

type Middleware

type Middleware struct {
	ResFunc func(r *ghttp.Request, err error)
}

func NewMiddleware

func NewMiddleware(resFunc ...func(r *ghttp.Request, err error)) *Middleware

func (*Middleware) Auth

func (m *Middleware) Auth(r *ghttp.Request)

type TokenStyle

type TokenStyle string
const (
	TokenStyleUUID    TokenStyle = "uuid"
	TokenStyleRand64  TokenStyle = "rand64"
	TokenStyleRand128 TokenStyle = "rand128"
)

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL