生产环境用Go语言完成微服务搭建和业务融入

业务场景:已经有一套在运行的php项目,但是性能和灵活性不足。需要开发部署一套go语言服务,但是要能兼容前项目的鉴权规则。那么我们除了将php的鉴权模块独立出来,放到网关,再就是在go服务里写一个同逻辑的中间件。

我发现了项目中这张表里存了用户的token和创建销毁时间,也就不难猜出,原来的后端是通过这里判断token有效和时间的。

那么作为后来者,我也可以通过这张表去对比前端携带的token是否合法,就有了以下的代码。

Go 复制代码
// Token验证中间件(仅通过token验证)
func TokenAuthMiddleware() gin.HandlerFunc {
	return func(c *gin.Context) {
		// 从请求头获取token
		token := c.GetHeader("Authorization")
		if token == "" {
			c.JSON(http.StatusUnauthorized, gin.H{
				"success": false,
				"error":   "未授权",
			})
			c.Abort()
			return
		}

		// 去除可能的"Bearer "前缀
		if strings.HasPrefix(token, "Bearer ") {
			token = strings.TrimPrefix(token, "Bearer ")
		}
		log.Printf("前端token%s:", token)
		// 验证token有效性
		isValid := verifyToken(token)
		if !isValid {
			c.JSON(http.StatusUnauthorized, gin.H{
				"success": false,
				"error":   "未授权",
			})
			c.Abort()
			return
		}

		// token验证通过,继续执行后续逻辑
		c.Next()
	}
}

// 通过token验证有效性
func verifyToken(token string) bool {
	// 查询token对应的记录
	type UserToken struct {
		Createtime int64 `json:"createtime"`
		Expiretime int64 `json:"expiretime"`
	}

	var userToken UserToken

	// 查询该token对应的记录
	query := `
        SELECT createtime, expiretime 
        FROM fa_user_token 
        WHERE token = ? 
        LIMIT 1
    `

	err := dbManager.GetDB().QueryRow(query, token).Scan(
		&userToken.Createtime,
		&userToken.Expiretime,
	)

	if err != nil {
		if err == sql.ErrNoRows {
			log.Printf("token不存在: %s", token)
		} else {
			log.Printf("查询token失败: %s, 错误: %v", token, err)
		}
		return false
	}

	// 获取当前时间戳(秒级)
	currentTime := time.Now().Unix()

	// 验证是否过期
	isExpired := false

	// 1. 验证是否超过两个月(5184000秒 = 60天)
	twoMonthsAgo := currentTime - 5184000
	//2592000 一个月
	//1296000 半个月
	if userToken.Createtime < twoMonthsAgo {
		isExpired = true
		log.Printf("token已超过两个月: %s", token)
	}

	// 2. 检查是否已主动退出/销毁(expiretime字段有值且小于当前时间)
	if userToken.Expiretime > 0 {
		if currentTime > userToken.Expiretime {
			isExpired = true
			log.Printf("token已主动退出/销毁: %s, 销毁时间: %d", token, userToken.Expiretime)
		} else {
			log.Printf("token有效期内: %s, 过期时间: %d", token, userToken.Expiretime)
		}
	} else {
		log.Printf("token无过期时间设置: %s", token)
	}

	if isExpired {
		return false
	}

	log.Printf("token验证成功: %s", token)
	return true
}

使用时作为中间件放入到函数中当做参数传入就ok了。

相关推荐
源心锁1 天前
丧心病狂!在浏览器全天候记录用户行为排障
前端·架构
Tony Bai1 天前
【分布式系统】03 复制(上):“权威中心”的秩序 —— 主从架构、一致性与权衡
大数据·数据库·分布式·架构
AIagenttest1 天前
2026年智能招聘管理系统测评:从流程协同到算力执行的架构跨越
架构
Mr_sun.1 天前
微服务框架课程
微服务·云原生·架构
伟兮1 天前
iOS日志系统设计
架构
国科安芯1 天前
卫星通讯导航FPGA供电单元DCDC芯片ASP4644S2B可靠性分析
单片机·嵌入式硬件·fpga开发·架构·安全性测试
鱼跃鹰飞1 天前
DDD中的防腐层
java·设计模式·架构
攀登的牵牛花1 天前
前端向架构突围系列 - 框架设计(五):契约继承原则
前端·架构
羊羊羊i1 天前
使用Informer监听K8s资源
云原生·容器·kubernetes
lhrimperial1 天前
企业智能知识库助手落地实践:从RAG到Multi-Agent
java·spring cloud·微服务·系统架构·知识图谱