| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291 | package handlerimport (	"errors"	"fmt"	"gas-cylinder-api/app/admin/model"	"gas-cylinder-api/common"	"gas-cylinder-api/common/global"	"github.com/gin-gonic/gin"	"github.com/go-redis/redis/v7"	"github.com/go-sql-driver/mysql"	"github.com/mssola/user_agent"	"gogs.baozhida.cn/zoie/OAuth-core/api"	"gogs.baozhida.cn/zoie/OAuth-core/pkg"	jwt "gogs.baozhida.cn/zoie/OAuth-core/pkg/jwtauth"	"gogs.baozhida.cn/zoie/OAuth-core/pkg/jwtauth/user"	"gogs.baozhida.cn/zoie/OAuth-core/pkg/response"	"gogs.baozhida.cn/zoie/OAuth-core/sdk"	"gogs.baozhida.cn/zoie/OAuth-core/sdk/config"	"gorm.io/gorm"	"net/http"	"strings")func PayloadFunc(data interface{}) jwt.MapClaims {	if v, ok := data.(map[string]interface{}); ok {		u, _ := v["user"].(SysUser)		r, _ := v["role"].(SysRole)		d, _ := v["dept"].(SysDept)		single, _ := v["single"].(bool)		return jwt.MapClaims{			jwt.UUIDKey:      u.Uuid,			jwt.IdentityKey:  u.Id,			jwt.RoleIdKey:    r.Id,			jwt.RoleKey:      r.RoleKey,			jwt.UserNameKey:  u.Username,			jwt.DataScopeKey: r.DataScope,			jwt.RoleNameKey:  r.Name,			jwt.SingleKey:    single,			jwt.DeptIdKey:    u.DeptId,			jwt.DeptNameKey:  d.DeptName,		}	}	return jwt.MapClaims{}}func IdentityHandler(c *gin.Context) interface{} {	claims := jwt.ExtractClaims(c)	return map[string]interface{}{		"UUIDKey":     claims["uuid"],		"IdentityKey": claims["identity"],		"UserName":    claims["username"],		"RoleName":    claims["roleName"],		"RoleKey":     claims["roleKey"],		"Id":          claims["identity"],		"RoleId":      claims["roleId"],		"DataScope":   claims["dataScope"],		"single":      claims["single"],		"DeptId":      claims["deptId"],		"DeptName":    claims["deptName"],	}}// Authenticator 登录认证// Update 登录认证// @Summary 登录认证// @Description 登录认证// @Tags 登录// @Accept  application/json// @Product application/json// @Param data body Login true "body"// @Success 200 {object} response.Response "{"code": 200, "data": [...]}"// @Router /api/login [post]func Authenticator(c *gin.Context) (interface{}, error) {	log := api.GetRequestLogger(c)	ormDB, err := pkg.GetOrm(c)	if err != nil {		log.Errorf("get db error, %s", err.Error())		response.Error(c, 500, err, "数据库连接获取失败")		return nil, jwt.ErrFailedAuthentication	}	var loginVals Login	var status = "2"	var msg = "登录成功"	var username = ""	defer func() {		LoginLogToDB(c, status, msg, username)	}()	if err = c.ShouldBind(&loginVals); err != nil {		username = loginVals.Username		msg = "数据解析失败"		status = "1"		return nil, jwt.ErrFailedAuthentication	}	//if config.ApplicationConfig.Mode != "dev" {	//	if !captcha.Verify(loginVals.UUID, loginVals.Code, true) {	//		username = loginVals.Username	//		msg = "验证码错误"	//		status = "1"	//	//		return nil, jwt.ErrInvalidVerificationCode	//	}	//}	var u SysUser	var role SysRole	var dept SysDept	var e error	if loginVals.Type == 1 {		u, role, dept, e = loginVals.GetUser(ormDB)		if e != nil {			msg = e.Error()			status = "1"			log.Warnf("%s login failed!", username)			return nil, jwt.ErrFailedAuthentication		}	}	if loginVals.Type == 2 {		u, role, dept, e = loginVals.GetUserByCode(ormDB)		if e != nil {			msg = e.Error()			status = "1"			log.Warnf("%s login failed!", username)			return nil, jwt.ErrFailedSmsVerifyCode		}	}	if loginVals.Type == 0 {		return nil, jwt.ErrFailedAuthentication	}	username = loginVals.Username	var single bool	//single, err = GetSingleLogin(c)	//if err != nil {	//	return nil, err	//}	return map[string]interface{}{"user": u, "role": role, "dept": dept, "single": single, "mobile": loginVals.Mobile}, nil}// LoginLogToDB Write log to databasefunc LoginLogToDB(c *gin.Context, status string, msg string, username string) {	if !config.LoggerConfig.EnabledDB {		return	}	log := api.GetRequestLogger(c)	l := make(map[string]interface{})	ua := user_agent.New(c.Request.UserAgent())	l["ipaddr"] = common.GetClientIP(c)	l["loginTime"] = pkg.GetCurrentTime()	l["status"] = status	l["remark"] = c.Request.UserAgent()	browserName, browserVersion := ua.Browser()	l["browser"] = browserName + " " + browserVersion	l["os"] = ua.OS()	l["platform"] = ua.Platform()	l["username"] = username	l["msg"] = msg	q := sdk.Runtime.GetMemoryQueue(c.Request.Host)	message, err := sdk.Runtime.GetStreamMessage("", global.LoginLog, l)	if err != nil {		log.Errorf("GetStreamMessage error, %s", err.Error())		//日志报错错误,不中断请求	} else {		err = q.Append(message)		if err != nil {			log.Errorf("Append message error, %s", err.Error())		}	}}// LogOut 退出登录// @Summary 退出登录// @Description 退出登录// @Description LoginHandler can be used by clients to get a jwt token.// @Description Reply will be of the form {"token": "TOKEN"}.// @Tags 登录// @Accept  application/json// @Product application/json// @Success 200 {string} string "{"code": 200, "msg": "成功退出系统"}"// @Router /logout [post]// @Security Bearerfunc LogOut(c *gin.Context) {	LoginLogToDB(c, "2", "退出成功", user.GetUserName(c))	c.JSON(http.StatusOK, gin.H{		"code": 200,		"msg":  "退出成功",	})}func Authorizator(data interface{}, c *gin.Context) bool {	if v, ok := data.(map[string]interface{}); ok {		u, _ := v["user"].(model.SysUser)		r, _ := v["role"].(model.SysRole)		d, _ := v["dept"].(model.SysDept)		single, _ := v["single"].(bool)		c.Set("uuid", u.Uuid)		c.Set("identity", u.Id)		c.Set("userName", u.Username)		c.Set("roleName", r.Name)		c.Set("roleKey", r.RoleKey)		c.Set("userId", u.Id)		c.Set("roleId", r.Id)		c.Set("single", single)		c.Set("dataScope", r.DataScope)		c.Set("deptId", u.DeptId)		c.Set("deptName", d.Name)		return true	}	return false}func Unauthorized(c *gin.Context, code int, message string) {	c.JSON(http.StatusOK, gin.H{		"code": code,		"msg":  message,	})}// 保存token到redisfunc SaveNewestToken(c *gin.Context, userId int64, token string, expire int64) error {	key := fmt.Sprintf("%s:%d", "bzd.oauth.token", userId)	return sdk.Runtime.GetCacheAdapter().Set(key, token, int(expire))}// redis从redis获取tokenfunc GetNewestToken(c *gin.Context, userId int64) (string, error) {	key := fmt.Sprintf("%s:%d", "bzd.oauth.token", userId)	return sdk.Runtime.GetCacheAdapter().Get(key)}func GetSingleLogin(c *gin.Context) (bool, error) {	log := api.GetRequestLogger(c)	ormDB, err := pkg.GetOrm(c)	if err != nil {		log.Errorf("get db error, %s", err.Error())		response.Error(c, 500, err, "数据库连接获取失败")		return false, err	}	//result := map[string]interface{}{}	var result string	err = ormDB.Table("sys_config").Select("config_value").Where("config_key = ? ", "sys_single_login").Scan(&result).Error	if err != nil {		log.Errorf("get sys_config error, %s", err.Error())		if errors.Is(err, gorm.ErrRecordNotFound) || err.(*mysql.MySQLError).Number == 1146 {			// 默认为非单一登录			return false, nil		}		return false, err	}	if result == "是" {		return true, nil	}	return false, nil}func SetEnterDeptId(c *gin.Context, newToken string, userId int64) error {	oldToken := ""	list := strings.Split(c.Request.Header.Get("Authorization"), ".")	if len(list) > 0 {		oldToken = list[len(list)-1]	} else {		return errors.New("token is null")	}	list2 := strings.Split(newToken, ".")	newToken2 := list2[len(list2)-1]	deptIdStr, err := sdk.Runtime.GetCacheAdapter().Get(fmt.Sprintf("enter-dept-%s-%d", oldToken, userId))	if err == nil {		sdk.Runtime.GetCacheAdapter().Set(fmt.Sprintf("enter-dept-%s-%d", newToken2, userId), deptIdStr, int(config.JwtConfig.Timeout)+7200)		sdk.Runtime.GetCacheAdapter().Del(fmt.Sprintf("enter-dept-%s-%d", oldToken, userId))	}	deptName, err := sdk.Runtime.GetCacheAdapter().Get(fmt.Sprintf("enter-dept-name-%s-%d", oldToken, userId))	if err == nil {		sdk.Runtime.GetCacheAdapter().Set(fmt.Sprintf("enter-dept-name-%s-%d", newToken2, userId), deptName, int(config.JwtConfig.Timeout)+7200)		sdk.Runtime.GetCacheAdapter().Del(fmt.Sprintf("enter-dept-name-%s-%d", oldToken, userId))	}	if err == redis.Nil {		return nil	}	return err}
 |