From ed9ca764d4c1022d8fa7fc0b468a43312c8318db Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=A5=87=E6=B7=BC=EF=BC=88piexlmax?= <303176530@qq.com> Date: Wed, 24 Aug 2022 11:36:28 +0800 Subject: [PATCH 01/10] =?UTF-8?q?=E5=A2=9E=E5=8A=A0=E8=8C=83=E5=9B=B4?= =?UTF-8?q?=E6=90=9C=E7=B4=A2=E8=87=AA=E5=8A=A8=E5=8C=96=EF=BC=8C=E8=B0=83?= =?UTF-8?q?=E6=95=B4=E4=BA=86=E4=B8=80=E4=BA=9B=E5=B7=B2=E7=9F=A5=E7=9A=84?= =?UTF-8?q?bug=20(#1206)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * 测试build是否成功 * 增加自动化范围搜索,调整字典查询 * 调整默认用户名 * 避免页面加载后立即触发一次验证,页面出现一片红色的警告的情况 * 避免登录接口成功后,push 时间太长但是加载框已经消失,让人误以为登录失败 Co-authored-by: mngma --- .../autocode_template/server/request.go.tpl | 9 ++++ .../autocode_template/server/service.go.tpl | 23 ++++------ .../autocode_template/web/table.vue.tpl | 43 +++++++++++++++++-- server/source/system/user.go | 4 +- web/src/pinia/modules/user.js | 2 +- web/src/view/login/index.vue | 1 + .../autoCode/component/fieldDialog.vue | 13 +++++- 7 files changed, 74 insertions(+), 21 deletions(-) diff --git a/server/resource/autocode_template/server/request.go.tpl b/server/resource/autocode_template/server/request.go.tpl index b6c2e3d10..d2fdfd85c 100644 --- a/server/resource/autocode_template/server/request.go.tpl +++ b/server/resource/autocode_template/server/request.go.tpl @@ -3,9 +3,18 @@ package request import ( "github.com/flipped-aurora/gin-vue-admin/server/model/{{.Package}}" "github.com/flipped-aurora/gin-vue-admin/server/model/common/request" + "time" ) type {{.StructName}}Search struct{ {{.Package}}.{{.StructName}} + StartCreatedAt *time.Time `json:"startCreatedAt" form:"startCreatedAt"` + EndCreatedAt *time.Time `json:"endCreatedAt" form:"endCreatedAt"` + {{- range .Fields}} + {{- if eq .FieldSearchType "BETWEEN" "NOT BETWEEN"}} + Start{{.FieldName}} *{{.FieldType}} `json:"start{{.FieldName}}" form:"start{{.FieldName}}"` + End{{.FieldName}} *{{.FieldType}} `json:"end{{.FieldName}}" form:"end{{.FieldName}}"` + {{- end }} + {{- end }} request.PageInfo } diff --git a/server/resource/autocode_template/server/service.go.tpl b/server/resource/autocode_template/server/service.go.tpl index b578d31d6..610871158 100644 --- a/server/resource/autocode_template/server/service.go.tpl +++ b/server/resource/autocode_template/server/service.go.tpl @@ -54,29 +54,24 @@ func ({{.Abbreviation}}Service *{{.StructName}}Service)Get{{.StructName}}InfoLis db := global.GVA_DB.Model(&{{.Package}}.{{.StructName}}{}) var {{.Abbreviation}}s []{{.Package}}.{{.StructName}} // 如果有条件搜索 下方会自动创建搜索语句 + if info.StartCreatedAt !=nil && info.EndCreatedAt !=nil { + db = db.Where("created_at BETWEEN ? AND ?", info.StartCreatedAt, info.EndCreatedAt) + } {{- range .Fields}} {{- if .FieldSearchType}} {{- if eq .FieldType "string" }} if info.{{.FieldName}} != "" { db = db.Where("{{.ColumnName}} {{.FieldSearchType}} ?",{{if eq .FieldSearchType "LIKE"}}"%"+ {{ end }}info.{{.FieldName}}{{if eq .FieldSearchType "LIKE"}}+"%"{{ end }}) } - {{- else if eq .FieldType "bool" }} + {{- else if eq .FieldSearchType "BETWEEN" "NOT BETWEEN"}} + if info.Start{{.FieldName}} != nil && info.End{{.FieldName}} != nil { + db = db.Where("{{.ColumnName}} {{.FieldSearchType}} ? AND ? ",info.Start{{.FieldName}},info.End{{.FieldName}}) + } + {{- else}} if info.{{.FieldName}} != nil { db = db.Where("{{.ColumnName}} {{.FieldSearchType}} ?",{{if eq .FieldSearchType "LIKE"}}"%"+{{ end }}info.{{.FieldName}}{{if eq .FieldSearchType "LIKE"}}+"%"{{ end }}) } - {{- else if eq .FieldType "int" }} - if info.{{.FieldName}} != nil { - db = db.Where("{{.ColumnName}} {{.FieldSearchType}} ?",{{if eq .FieldSearchType "LIKE"}}"%"+{{ end }}info.{{.FieldName}}{{if eq .FieldSearchType "LIKE"}}+"%"{{ end }}) - } - {{- else if eq .FieldType "float64" }} - if info.{{.FieldName}} != nil { - db = db.Where("{{.ColumnName}} {{.FieldSearchType}} ?",{{if eq .FieldSearchType "LIKE"}}"%"+{{ end }}info.{{.FieldName}}{{if eq .FieldSearchType "LIKE"}}+"%"{{ end }}) - } - {{- else if eq .FieldType "time.Time" }} - if info.{{.FieldName}} != nil { - db = db.Where("{{.ColumnName}} {{.FieldSearchType}} ?",{{if eq .FieldSearchType "LIKE"}}"%"+{{ end }}info.{{.FieldName}}{{if eq .FieldSearchType "LIKE"}}+"%"{{ end }}) - } - {{- end }} + {{- end }} {{- end }} {{- end }} err = db.Count(&total).Error diff --git a/server/resource/autocode_template/web/table.vue.tpl b/server/resource/autocode_template/web/table.vue.tpl index 1ab94c563..a6b99d0ee 100644 --- a/server/resource/autocode_template/web/table.vue.tpl +++ b/server/resource/autocode_template/web/table.vue.tpl @@ -2,6 +2,11 @@
From 7d771a56e6b15b18ec7f2932fab0a7c858572704 Mon Sep 17 00:00:00 2001 From: myface-wang <240298530@qq.com> Date: Thu, 1 Sep 2022 17:11:20 +0800 Subject: [PATCH 04/10] =?UTF-8?q?=E4=BC=98=E5=8C=96=EF=BC=8C=E5=90=88?= =?UTF-8?q?=E5=B9=B6update=E6=96=B9=E6=B3=95=20(#1212)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- server/service/example/exa_breakpoint_continue.go | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/server/service/example/exa_breakpoint_continue.go b/server/service/example/exa_breakpoint_continue.go index 7363c7a2b..8a35983cf 100644 --- a/server/service/example/exa_breakpoint_continue.go +++ b/server/service/example/exa_breakpoint_continue.go @@ -56,7 +56,11 @@ func (e *FileUploadAndDownloadService) CreateFileChunk(id uint, fileChunkPath st func (e *FileUploadAndDownloadService) DeleteFileChunk(fileMd5 string, filePath string) error { var chunks []example.ExaFileChunk var file example.ExaFile - err := global.GVA_DB.Where("file_md5 = ? ", fileMd5).First(&file).Update("IsFinish", true).Update("file_path", filePath).Error + err := global.GVA_DB.Where("file_md5 = ? ", fileMd5).First(&file). + Updates(map[string]interface{}{ + "IsFinish": true, + "file_path": filePath, + }).Error if err != nil { return err } From 34b6e5ebaeb09eeee9c7514879316eab154e7ce9 Mon Sep 17 00:00:00 2001 From: piexl <303176530@qq.com> Date: Fri, 2 Sep 2022 17:02:17 +0800 Subject: [PATCH 05/10] =?UTF-8?q?a=E6=A0=87=E7=AD=BE=E6=A0=B7=E5=BC=8F?= =?UTF-8?q?=E6=81=A2=E5=A4=8D=E4=BE=BF=E4=BA=8E=E9=9B=86=E6=88=90=E5=AF=8C?= =?UTF-8?q?=E6=96=87=E6=9C=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- web/src/style/main.scss | 18 +----------------- 1 file changed, 1 insertion(+), 17 deletions(-) diff --git a/web/src/style/main.scss b/web/src/style/main.scss index 1a42bed02..689bf8366 100644 --- a/web/src/style/main.scss +++ b/web/src/style/main.scss @@ -461,22 +461,6 @@ a { text-decoration: none; } -a:link { - color: #fff; -} - -a:visited { - color: #fff; -} - -a:hover { - color: #fff; -} - -a:active { - color: #fff; -} - input::-ms-clear { display: none; } @@ -597,7 +581,7 @@ li { } .aside { .el-menu--collapse { - >.el-menu-item{ + >.el-menu-item { display: flex; justify-content: center; } From f606c7c89118a0d5ff170bdae4faab9294c082fe Mon Sep 17 00:00:00 2001 From: piexlmax <303176530@qq.com> Date: Sat, 3 Sep 2022 13:26:20 +0800 Subject: [PATCH 06/10] =?UTF-8?q?=E8=B0=83=E6=95=B4casbin=E4=B8=BA?= =?UTF-8?q?=E7=BC=93=E5=AD=98=E6=A8=A1=E5=BC=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- server/service/system/sys_api.go | 33 +++++++++++++++---- server/service/system/sys_autocode_history.go | 13 +++++++- server/service/system/sys_casbin.go | 20 ++++++++--- 3 files changed, 53 insertions(+), 13 deletions(-) diff --git a/server/service/system/sys_api.go b/server/service/system/sys_api.go index 5bcf61534..3e35d94a8 100644 --- a/server/service/system/sys_api.go +++ b/server/service/system/sys_api.go @@ -3,7 +3,6 @@ package system import ( "errors" "fmt" - "github.com/flipped-aurora/gin-vue-admin/server/global" "github.com/flipped-aurora/gin-vue-admin/server/model/common/request" "github.com/flipped-aurora/gin-vue-admin/server/model/system" @@ -44,7 +43,15 @@ func (apiService *ApiService) DeleteApi(api system.SysApi) (err error) { if err != nil { return err } - CasbinServiceApp.ClearCasbin(1, entity.Path, entity.Method) + success := CasbinServiceApp.ClearCasbin(1, entity.Path, entity.Method) + if !success { + return errors.New(entity.Path + ":" + entity.Method + "casbin同步清理失败") + } + e := CasbinServiceApp.Casbin() + err = e.InvalidateCache() + if err != nil { + return err + } return nil } @@ -166,10 +173,22 @@ func (apiService *ApiService) UpdateApi(api system.SysApi) (err error) { //@return: err error func (apiService *ApiService) DeleteApisByIds(ids request.IdsReq) (err error) { - err = global.GVA_DB.Delete(&[]system.SysApi{}, "id in ?", ids.Ids).Error + var apis []system.SysApi + err = global.GVA_DB.Find(&apis, "id in ?", ids.Ids).Delete(&apis).Error + if err != nil { + return err + } else { + for _, sysApi := range apis { + success := CasbinServiceApp.ClearCasbin(1, sysApi.Path, sysApi.Method) + if !success { + return errors.New(sysApi.Path + ":" + sysApi.Method + "casbin同步清理失败") + } + } + e := CasbinServiceApp.Casbin() + err = e.InvalidateCache() + if err != nil { + return err + } + } return err } - -func (apiService *ApiService) DeleteApiByIds(ids []string) (err error) { - return global.GVA_DB.Delete(&system.SysApi{}, "id in ?", ids).Error -} diff --git a/server/service/system/sys_autocode_history.go b/server/service/system/sys_autocode_history.go index 078111f22..b2d2f5124 100644 --- a/server/service/system/sys_autocode_history.go +++ b/server/service/system/sys_autocode_history.go @@ -5,6 +5,7 @@ import ( "fmt" systemReq "github.com/flipped-aurora/gin-vue-admin/server/model/system/request" "path/filepath" + "strconv" "strings" "time" @@ -67,7 +68,17 @@ func (autoCodeHistoryService *AutoCodeHistoryService) RollBack(info *systemReq.R return err } // 清除API表 - err := ApiServiceApp.DeleteApiByIds(strings.Split(md.ApiIDs, ";")) + + ids := request.IdsReq{} + idsStr := strings.Split(md.ApiIDs, ";") + for i := range idsStr { + id, err := strconv.Atoi(idsStr[i]) + if err != nil { + return err + } + ids.Ids = append(ids.Ids, id) + } + err := ApiServiceApp.DeleteApisByIds(ids) if err != nil { global.GVA_LOG.Error("ClearTag DeleteApiByIds:", zap.Error(err)) } diff --git a/server/service/system/sys_casbin.go b/server/service/system/sys_casbin.go index 8959b531b..2dbd357a5 100644 --- a/server/service/system/sys_casbin.go +++ b/server/service/system/sys_casbin.go @@ -35,6 +35,10 @@ func (casbinService *CasbinService) UpdateCasbin(AuthorityID uint, casbinInfos [ if !success { return errors.New("存在相同api,添加失败,请联系管理员") } + err := e.InvalidateCache() + if err != nil { + return err + } return nil } @@ -49,6 +53,11 @@ func (casbinService *CasbinService) UpdateCasbinApi(oldPath string, newPath stri "v1": newPath, "v2": newMethod, }).Error + e := casbinService.Casbin() + err = e.InvalidateCache() + if err != nil { + return err + } return err } @@ -89,11 +98,11 @@ func (casbinService *CasbinService) ClearCasbin(v int, p ...string) bool { //@return: *casbin.Enforcer var ( - syncedEnforcer *casbin.SyncedEnforcer + cachedEnforcer *casbin.CachedEnforcer once sync.Once ) -func (casbinService *CasbinService) Casbin() *casbin.SyncedEnforcer { +func (casbinService *CasbinService) Casbin() *casbin.CachedEnforcer { once.Do(func() { a, _ := gormadapter.NewAdapterByDB(global.GVA_DB) text := ` @@ -117,8 +126,9 @@ func (casbinService *CasbinService) Casbin() *casbin.SyncedEnforcer { zap.L().Error("字符串加载模型失败!", zap.Error(err)) return } - syncedEnforcer, _ = casbin.NewSyncedEnforcer(m, a) + cachedEnforcer, _ = casbin.NewCachedEnforcer(m, a) + cachedEnforcer.SetExpireTime(60 * 60) + _ = cachedEnforcer.LoadPolicy() }) - _ = syncedEnforcer.LoadPolicy() - return syncedEnforcer + return cachedEnforcer } From b9a30b9ffe28fc281e5edda0041bdc0b180a2e17 Mon Sep 17 00:00:00 2001 From: ipanghu Date: Tue, 6 Sep 2022 10:17:05 +0800 Subject: [PATCH 07/10] =?UTF-8?q?[Feature]=20=E6=96=B0=E5=A2=9E=E9=A1=B5?= =?UTF-8?q?=E9=9D=A2=E5=88=87=E6=8D=A2=E8=BF=9B=E5=BA=A6=E6=9D=A1=20(#1213?= =?UTF-8?q?)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 新增页面切换进度条 --- web/package.json | 1 + web/src/main.js | 13 +++++++++++++ web/src/permission.js | 12 ++++++++++++ web/src/style/base.scss | 6 +++++- 4 files changed, 31 insertions(+), 1 deletion(-) diff --git a/web/package.json b/web/package.json index 0555be15d..9cc4aa3a1 100644 --- a/web/package.json +++ b/web/package.json @@ -18,6 +18,7 @@ "highlight.js": "^10.6.0", "marked": "^2.0.0", "mitt": "^3.0.0", + "nprogress": "^0.2.0", "path": "^0.12.7", "pinia": "^2.0.9", "qs": "^6.8.0", diff --git a/web/src/main.js b/web/src/main.js index cbe804ae0..4a4f25c53 100644 --- a/web/src/main.js +++ b/web/src/main.js @@ -12,6 +12,19 @@ import run from '@/core/gin-vue-admin.js' import auth from '@/directive/auth' import { store } from '@/pinia' import App from './App.vue' +/** + * @description 导入加载进度条,防止首屏加载时间过长,用户等待 + * + * */ +import Nprogress from 'nprogress' +import 'nprogress/nprogress.css' +Nprogress.configure({ showSpinner: false, ease: 'ease', speed: 500 }) +Nprogress.start() + +/** + * 无需在这块结束,会在路由中间件中结束此块内容 + * */ + const app = createApp(App) app.config.productionTip = false diff --git a/web/src/permission.js b/web/src/permission.js index 619584149..954cfd5a0 100644 --- a/web/src/permission.js +++ b/web/src/permission.js @@ -2,6 +2,7 @@ import { useUserStore } from '@/pinia/modules/user' import { useRouterStore } from '@/pinia/modules/router' import getPageTitle from '@/utils/page' import router from '@/router' +import Nprogress from 'nprogress' let asyncRouterFlag = 0 @@ -37,6 +38,7 @@ async function handleKeepAlive(to) { } router.beforeEach(async(to, from) => { + Nprogress.start() const userStore = useUserStore() to.meta.matched = [...to.matched] handleKeepAlive(to) @@ -99,3 +101,13 @@ router.beforeEach(async(to, from) => { } } }) + +router.afterEach(() => { + // 路由加载完成后关闭进度条 + Nprogress.done() +}) + +router.onError(() => { + // 路由发生错误后销毁进度条 + Nprogress.remove() +}) diff --git a/web/src/style/base.scss b/web/src/style/base.scss index f6a2eae8d..b3bda02ed 100644 --- a/web/src/style/base.scss +++ b/web/src/style/base.scss @@ -58,4 +58,8 @@ .keyword{ width: 220px; margin: 0 0 0 30px; -} \ No newline at end of file +} + +#nprogress .bar { + background: #4D70FF !important; //自定义颜色 +} From 3289405b17b793e5a4ea21fdac729edf2952780d Mon Sep 17 00:00:00 2001 From: piexlmax <303176530@qq.com> Date: Wed, 7 Sep 2022 21:30:53 +0800 Subject: [PATCH 08/10] =?UTF-8?q?=E4=BF=AE=E5=A4=8D=E5=9B=9E=E6=BB=9Abug?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- server/service/system/sys_autocode_history.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/service/system/sys_autocode_history.go b/server/service/system/sys_autocode_history.go index b2d2f5124..a77673232 100644 --- a/server/service/system/sys_autocode_history.go +++ b/server/service/system/sys_autocode_history.go @@ -71,7 +71,7 @@ func (autoCodeHistoryService *AutoCodeHistoryService) RollBack(info *systemReq.R ids := request.IdsReq{} idsStr := strings.Split(md.ApiIDs, ";") - for i := range idsStr { + for i := range idsStr[0 : len(idsStr)-1] { id, err := strconv.Atoi(idsStr[i]) if err != nil { return err From ee7b9b0cff87326bd8df6922db8af50433937553 Mon Sep 17 00:00:00 2001 From: SliverHorn <503551462@qq.com> Date: Fri, 9 Sep 2022 11:33:58 +0800 Subject: [PATCH 09/10] =?UTF-8?q?update:=20=E7=94=A8=E6=88=B7=E9=BB=98?= =?UTF-8?q?=E8=AE=A4=E8=A7=92=E8=89=B2=E7=9A=84=E9=BB=98=E8=AE=A4=E8=B7=AF?= =?UTF-8?q?=E7=94=B1=E5=A6=82=E6=9E=9C=E4=B8=BA=E7=A9=BA=E5=88=99=E8=B5=8B?= =?UTF-8?q?=E5=80=BC404,=20=E5=85=AC=E5=85=B1=E6=96=B9=E6=B3=95=E6=8A=BD?= =?UTF-8?q?=E7=A6=BB=E5=B9=B6=E4=BC=98=E5=8C=96=20(#1215)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- server/service/system/sys_menu.go | 15 +++++++++++ server/service/system/sys_user.go | 41 +++---------------------------- 2 files changed, 19 insertions(+), 37 deletions(-) diff --git a/server/service/system/sys_menu.go b/server/service/system/sys_menu.go index 5af5b7588..8e13b04b6 100644 --- a/server/service/system/sys_menu.go +++ b/server/service/system/sys_menu.go @@ -218,3 +218,18 @@ func (menuService *MenuService) GetMenuAuthority(info *request.GetAuthorityId) ( // err = global.GVA_DB.Raw(sql, authorityId).Scan(&menus).Error return menus, err } + +// UserAuthorityDefaultRouter 用户角色默认路由检查 +// Author [SliverHorn](https://github.com/SliverHorn) +func (menuService *MenuService) UserAuthorityDefaultRouter(user *system.SysUser) { + var menuIds []string + err := global.GVA_DB.Model(&system.SysAuthorityMenu{}).Where("sys_authority_authority_id = ?", user.AuthorityId).Pluck("sys_base_menu_id", &menuIds).Error + if err != nil { + return + } + var am system.SysBaseMenu + err = global.GVA_DB.First(&am, "name = ? and id in (?)", user.Authority.DefaultRouter, menuIds).Error + if errors.Is(err, gorm.ErrRecordNotFound) { + user.Authority.DefaultRouter = "404" + } +} diff --git a/server/service/system/sys_user.go b/server/service/system/sys_user.go index 7a386820c..aef734fa3 100644 --- a/server/service/system/sys_user.go +++ b/server/service/system/sys_user.go @@ -32,6 +32,7 @@ func (userService *UserService) Register(u system.SysUser) (userInter system.Sys } //@author: [piexlmax](https://github.com/piexlmax) +//@author: [SliverHorn](https://github.com/SliverHorn) //@function: Login //@description: 用户登录 //@param: u *model.SysUser @@ -48,26 +49,8 @@ func (userService *UserService) Login(u *system.SysUser) (userInter *system.SysU if ok := utils.BcryptCheck(u.Password, user.Password); !ok { return nil, errors.New("密码错误") } - - var SysAuthorityMenus []system.SysAuthorityMenu - err = global.GVA_DB.Where("sys_authority_authority_id = ?", user.AuthorityId).Find(&SysAuthorityMenus).Error - if err != nil { - return - } - - var MenuIds []string - - for i := range SysAuthorityMenus { - MenuIds = append(MenuIds, SysAuthorityMenus[i].MenuId) - } - - var am system.SysBaseMenu - ferr := global.GVA_DB.First(&am, "name = ? and id in (?)", user.Authority.DefaultRouter, MenuIds).Error - if errors.Is(ferr, gorm.ErrRecordNotFound) { - user.Authority.DefaultRouter = "404" - } + MenuServiceApp.UserAuthorityDefaultRouter(&user) } - return &user, err } @@ -183,6 +166,7 @@ func (userService *UserService) SetUserInfo(req system.SysUser) error { } //@author: [piexlmax](https://github.com/piexlmax) +//@author: [SliverHorn](https://github.com/SliverHorn) //@function: GetUserInfo //@description: 获取用户信息 //@param: uuid uuid.UUID @@ -194,24 +178,7 @@ func (userService *UserService) GetUserInfo(uuid uuid.UUID) (user system.SysUser if err != nil { return reqUser, err } - - var SysAuthorityMenus []system.SysAuthorityMenu - err = global.GVA_DB.Where("sys_authority_authority_id = ?", reqUser.AuthorityId).Find(&SysAuthorityMenus).Error - if err != nil { - return - } - - var MenuIds []string - - for i := range SysAuthorityMenus { - MenuIds = append(MenuIds, SysAuthorityMenus[i].MenuId) - } - - var am system.SysBaseMenu - ferr := global.GVA_DB.First(&am, "name = ? and id in (?)", reqUser.Authority.DefaultRouter, MenuIds).Error - if errors.Is(ferr, gorm.ErrRecordNotFound) { - reqUser.Authority.DefaultRouter = "404" - } + MenuServiceApp.UserAuthorityDefaultRouter(&user) return reqUser, err } From b5c79be625688bc2da77ca9c9cbffab3a8f3ad53 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=A5=87=E6=B7=BC=EF=BC=88piexlmax?= <303176530@qq.com> Date: Tue, 13 Sep 2022 16:26:02 +0800 Subject: [PATCH 10/10] =?UTF-8?q?=E6=95=B4=E7=90=86=E9=85=8D=E7=BD=AE?= =?UTF-8?q?=E6=96=87=E4=BB=B6=EF=BC=8Cjwt=E8=BF=87=E6=9C=9F=E6=97=B6?= =?UTF-8?q?=E9=97=B4=E5=92=8C=E7=BC=93=E5=86=B2=E6=97=B6=E9=97=B4=E6=94=AF?= =?UTF-8?q?=E6=8C=811d2h3m4s=E4=BA=8B=E4=BB=B6=E7=B1=BB=E5=9E=8B=20(#1218)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * feat: human duration * Update config.yaml * 调整配置文件结构 Co-authored-by: songzhibin97 <718428482@qq.com> --- server/config.yaml | 146 ++++++++++++------------ server/config/jwt.go | 4 +- server/core/viper.go | 9 +- server/initialize/outer.go | 23 ++++ server/main.go | 6 +- server/middleware/jwt.go | 3 +- server/model/system/request/jwt.go | 2 +- server/service/system/jwt_black_list.go | 8 +- server/utils/human_duration.go | 23 ++++ server/utils/jwt.go | 13 ++- 10 files changed, 143 insertions(+), 94 deletions(-) create mode 100644 server/initialize/outer.go create mode 100644 server/utils/human_duration.go diff --git a/server/config.yaml b/server/config.yaml index d5110ba59..6859fd668 100644 --- a/server/config.yaml +++ b/server/config.yaml @@ -2,45 +2,43 @@ # jwt configuration jwt: - signing-key: 'qmPlus' - expires-time: 604800 - buffer-time: 86400 - issuer: 'qmPlus' - + signing-key: qmPlus + expires-time: 7d + buffer-time: 1d + issuer: qmPlus # zap logger configuration zap: - level: 'info' - prefix: '[github.com/flipped-aurora/gin-vue-admin/server]' - format: 'console' - director: 'log' - encode-level: 'LowercaseColorLevelEncoder' - stacktrace-key: 'stacktrace' - max-age: 30 # 默认日志留存默认以天为单位 + level: info + format: console + prefix: [github.com/flipped-aurora/gin-vue-admin/server] + director: log show-line: true + encode-level: LowercaseColorLevelEncoder + stacktrace-key: stacktrace log-in-console: true # redis configuration redis: db: 0 - addr: '127.0.0.1:6379' - password: '' + addr: 127.0.0.1:6379 + password: "" # email configuration email: - to: 'xxx@qq.com' + to: xxx@qq.com port: 465 - from: 'xxx@163.com' - host: 'smtp.163.com' + from: xxx@163.com + host: smtp.163.com is-ssl: true - secret: 'xxx' - nickname: 'test' + secret: xxx + nickname: test # system configuration system: - env: 'public' # Change to "develop" to skip authentication for development mode + env: public # Change to "develop" to skip authentication for development mode addr: 8888 - db-type: 'mysql' - oss-type: 'local' # 控制oss选择走本地还是 七牛等其他仓 自行增加其他oss仓可以在 server/utils/upload/upload.go 中 NewOss函数配置 + db-type: mysql + oss-type: local # 控制oss选择走本地还是 七牛等其他仓 自行增加其他oss仓可以在 server/utils/upload/upload.go 中 NewOss函数配置 use-redis: false # 使用redis use-multipoint: false # IP限制次数 一个小时15000次 @@ -57,12 +55,12 @@ captcha: # mysql connect configuration # 未初始化之前请勿手动修改数据库信息!!!如果一定要手动初始化请看(https://gin-vue-admin.com/docs/first_master) mysql: - path: '' - port: '' - config: '' - db-name: '' - username: '' - password: '' + path: "" + port: "" + config: "" + db-name: "" + username: "" + password: "" max-idle-conns: 10 max-open-conns: 100 log-mode: "" @@ -71,12 +69,12 @@ mysql: # pgsql connect configuration # 未初始化之前请勿手动修改数据库信息!!!如果一定要手动初始化请看(https://gin-vue-admin.com/docs/first_master) pgsql: - path: '' - port: '' - config: '' - db-name: '' - username: '' - password: '' + path: "" + port: "" + config: "" + db-name: "" + username: "" + password: "" max-idle-conns: 10 max-open-conns: 100 log-mode: "" @@ -86,12 +84,12 @@ db-list: - disabled: true # 是否启用 type: "" # 数据库的类型,目前支持mysql、pgsql alias-name: "" # 数据库的名称,注意: alias-name 需要在db-list中唯一 - path: '' - port: '' - config: '' - db-name: '' - username: '' - password: '' + path: "" + port: "" + config: "" + db-name: "" + username: "" + password: "" max-idle-conns: 10 max-open-conns: 100 log-mode: "" @@ -100,8 +98,8 @@ db-list: # local configuration local: - path: 'uploads/file' # 访问路径 - store-path: 'uploads/file' # 存储路径 + path: uploads/file + store-path: uploads/file # autocode configuration autocode: @@ -124,67 +122,67 @@ autocode: # qiniu configuration (请自行七牛申请对应的 公钥 私钥 bucket 和 域名地址) qiniu: - zone: 'ZoneHuaDong' - bucket: '' - img-path: '' + zone: ZoneHuaDong + bucket: "" + img-path: "" use-https: false - access-key: '' - secret-key: '' + access-key: "" + secret-key: "" use-cdn-domains: false # aliyun oss configuration aliyun-oss: - endpoint: 'yourEndpoint' - access-key-id: 'yourAccessKeyId' - access-key-secret: 'yourAccessKeySecret' - bucket-name: 'yourBucketName' - bucket-url: 'yourBucketUrl' - base-path: 'yourBasePath' + endpoint: yourEndpoint + access-key-id: yourAccessKeyId + access-key-secret: yourAccessKeySecret + bucket-name: yourBucketName + bucket-url: yourBucketUrl + base-path: yourBasePath # tencent cos configuration tencent-cos: - bucket: 'xxxxx-10005608' - region: 'ap-shanghai' - secret-id: 'xxxxxxxx' - secret-key: 'xxxxxxxx' - base-url: 'https://gin.vue.admin' - path-prefix: 'github.com/flipped-aurora/gin-vue-admin/server' + bucket: xxxxx-10005608 + region: ap-shanghai + secret-id: your-secret-id + secret-key: your-secret-key + base-url: https://gin.vue.admin + path-prefix: github.com/flipped-aurora/gin-vue-admin/server # aws s3 configuration (minio compatible) aws-s3: bucket: xxxxx-10005608 region: ap-shanghai - endpoint: '' + endpoint: "" s3-force-path-style: false disable-ssl: false - secret-id: xxxxxxxx - secret-key: xxxxxxxx + secret-id: your-secret-id + secret-key: your-secret-key base-url: https://gin.vue.admin path-prefix: github.com/flipped-aurora/gin-vue-admin/server # huawei obs configuration hua-wei-obs: - path: 'you-path' - bucket: 'you-bucket' - endpoint: 'you-endpoint' - access-key: 'you-access-key' - secret-key: 'you-secret-key' + path: you-path + bucket: you-bucket + endpoint: you-endpoint + access-key: you-access-key + secret-key: you-secret-key # excel configuration excel: - dir: './resource/excel/' + dir: ./resource/excel/ # timer task db clear table Timer: start: true spec: "@daily" # 定时任务详细配置参考 https://pkg.go.dev/github.com/robfig/cron/v3 detail: - - tableName: "sys_operation_records" - compareField: "created_at" - interval: "2160h" - - tableName: "jwt_blacklists" - compareField: "created_at" - interval: "168h" + - tableName: sys_operation_records + compareField: created_at + interval: 2160h + - tableName: jwt_blacklists + compareField: created_at + interval: 168h # 跨域配置 # 需要配合 server/initialize/router.go#L32 使用 diff --git a/server/config/jwt.go b/server/config/jwt.go index 51979b6a2..c95d30dc1 100644 --- a/server/config/jwt.go +++ b/server/config/jwt.go @@ -2,7 +2,7 @@ package config type JWT struct { SigningKey string `mapstructure:"signing-key" json:"signing-key" yaml:"signing-key"` // jwt签名 - ExpiresTime int64 `mapstructure:"expires-time" json:"expires-time" yaml:"expires-time"` // 过期时间 - BufferTime int64 `mapstructure:"buffer-time" json:"buffer-time" yaml:"buffer-time"` // 缓冲时间 + ExpiresTime string `mapstructure:"expires-time" json:"expires-time" yaml:"expires-time"` // 过期时间 + BufferTime string `mapstructure:"buffer-time" json:"buffer-time" yaml:"buffer-time"` // 缓冲时间 Issuer string `mapstructure:"issuer" json:"issuer" yaml:"issuer"` // 签发者 } diff --git a/server/core/viper.go b/server/core/viper.go index 963717d40..3f67f9633 100644 --- a/server/core/viper.go +++ b/server/core/viper.go @@ -7,14 +7,12 @@ import ( "github.com/gin-gonic/gin" "os" "path/filepath" - "time" - "github.com/songzhibin97/gkit/cache/local_cache" + "github.com/fsnotify/fsnotify" + "github.com/spf13/viper" "github.com/flipped-aurora/gin-vue-admin/server/global" _ "github.com/flipped-aurora/gin-vue-admin/server/packfile" - "github.com/fsnotify/fsnotify" - "github.com/spf13/viper" ) // Viper // @@ -72,8 +70,5 @@ func Viper(path ...string) *viper.Viper { // root 适配性 根据root位置去找到对应迁移位置,保证root路径有效 global.GVA_CONFIG.AutoCode.Root, _ = filepath.Abs("..") - global.BlackCache = local_cache.NewCache( - local_cache.SetDefaultExpire(time.Second * time.Duration(global.GVA_CONFIG.JWT.ExpiresTime)), - ) return v } diff --git a/server/initialize/outer.go b/server/initialize/outer.go new file mode 100644 index 000000000..5d23aeb7f --- /dev/null +++ b/server/initialize/outer.go @@ -0,0 +1,23 @@ +package initialize + +import ( + "github.com/songzhibin97/gkit/cache/local_cache" + + "github.com/flipped-aurora/gin-vue-admin/server/global" + "github.com/flipped-aurora/gin-vue-admin/server/utils" +) + +func OtherInit() { + dr, err := utils.ParseDuration(global.GVA_CONFIG.JWT.ExpiresTime) + if err != nil { + panic(err) + } + _, err = utils.ParseDuration(global.GVA_CONFIG.JWT.BufferTime) + if err != nil { + panic(err) + } + + global.BlackCache = local_cache.NewCache( + local_cache.SetDefaultExpire(dr), + ) +} diff --git a/server/main.go b/server/main.go index 74b2786ef..8a0baa53f 100644 --- a/server/main.go +++ b/server/main.go @@ -1,10 +1,11 @@ package main import ( + "go.uber.org/zap" + "github.com/flipped-aurora/gin-vue-admin/server/core" "github.com/flipped-aurora/gin-vue-admin/server/global" "github.com/flipped-aurora/gin-vue-admin/server/initialize" - "go.uber.org/zap" ) //go:generate go env -w GO111MODULE=on @@ -21,7 +22,8 @@ import ( // @BasePath / func main() { global.GVA_VP = core.Viper() // 初始化Viper - global.GVA_LOG = core.Zap() // 初始化zap日志库 + initialize.OtherInit() + global.GVA_LOG = core.Zap() // 初始化zap日志库 zap.ReplaceGlobals(global.GVA_LOG) global.GVA_DB = initialize.Gorm() // gorm连接数据库 initialize.Timer() diff --git a/server/middleware/jwt.go b/server/middleware/jwt.go index a7075d021..25806e63f 100644 --- a/server/middleware/jwt.go +++ b/server/middleware/jwt.go @@ -54,7 +54,8 @@ func JWTAuth() gin.HandlerFunc { // c.Abort() //} if claims.ExpiresAt-time.Now().Unix() < claims.BufferTime { - claims.ExpiresAt = time.Now().Unix() + global.GVA_CONFIG.JWT.ExpiresTime + dr, _ := utils.ParseDuration(global.GVA_CONFIG.JWT.ExpiresTime) + claims.ExpiresAt = time.Now().Add(dr).Unix() newToken, _ := j.CreateTokenByOldToken(token, *claims) newClaims, _ := j.ParseToken(newToken) c.Header("new-token", newToken) diff --git a/server/model/system/request/jwt.go b/server/model/system/request/jwt.go index ee702ef97..5a7c78aab 100644 --- a/server/model/system/request/jwt.go +++ b/server/model/system/request/jwt.go @@ -1,7 +1,7 @@ package request import ( - "github.com/golang-jwt/jwt/v4" + jwt "github.com/golang-jwt/jwt/v4" uuid "github.com/satori/go.uuid" ) diff --git a/server/service/system/jwt_black_list.go b/server/service/system/jwt_black_list.go index 18fee92ea..836addc39 100644 --- a/server/service/system/jwt_black_list.go +++ b/server/service/system/jwt_black_list.go @@ -2,12 +2,12 @@ package system import ( "context" - "time" "go.uber.org/zap" "github.com/flipped-aurora/gin-vue-admin/server/global" "github.com/flipped-aurora/gin-vue-admin/server/model/system" + "github.com/flipped-aurora/gin-vue-admin/server/utils" ) type JwtService struct{} @@ -60,7 +60,11 @@ func (jwtService *JwtService) GetRedisJWT(userName string) (redisJWT string, err func (jwtService *JwtService) SetRedisJWT(jwt string, userName string) (err error) { // 此处过期时间等于jwt过期时间 - timer := time.Duration(global.GVA_CONFIG.JWT.ExpiresTime) * time.Second + dr, err := utils.ParseDuration(global.GVA_CONFIG.JWT.ExpiresTime) + if err != nil { + return err + } + timer := dr err = global.GVA_REDIS.Set(context.Background(), userName, jwt, timer).Err() return err } diff --git a/server/utils/human_duration.go b/server/utils/human_duration.go new file mode 100644 index 000000000..3a2c9b28c --- /dev/null +++ b/server/utils/human_duration.go @@ -0,0 +1,23 @@ +package utils + +import ( + "strconv" + "strings" + "time" +) + +func ParseDuration(d string) (time.Duration, error) { + dr, err := time.ParseDuration(d) + if err == nil { + return dr, nil + } + if strings.HasSuffix(d, "d") { + h := strings.TrimSuffix(d, "d") + hour, _ := strconv.Atoi(h) + dr = time.Hour * 24 * time.Duration(hour) + return dr, nil + } + + dv, err := strconv.ParseInt(d, 10, 64) + return time.Duration(dv), err +} diff --git a/server/utils/jwt.go b/server/utils/jwt.go index 569717766..1f9de19e5 100644 --- a/server/utils/jwt.go +++ b/server/utils/jwt.go @@ -4,9 +4,10 @@ import ( "errors" "time" + jwt "github.com/golang-jwt/jwt/v4" + "github.com/flipped-aurora/gin-vue-admin/server/global" "github.com/flipped-aurora/gin-vue-admin/server/model/system/request" - "github.com/golang-jwt/jwt/v4" ) type JWT struct { @@ -27,13 +28,15 @@ func NewJWT() *JWT { } func (j *JWT) CreateClaims(baseClaims request.BaseClaims) request.CustomClaims { + bf, _ := ParseDuration(global.GVA_CONFIG.JWT.BufferTime) + ep, _ := ParseDuration(global.GVA_CONFIG.JWT.ExpiresTime) claims := request.CustomClaims{ BaseClaims: baseClaims, - BufferTime: global.GVA_CONFIG.JWT.BufferTime, // 缓冲时间1天 缓冲时间内会获得新的token刷新令牌 此时一个用户会存在两个有效令牌 但是前端只留一个 另一个会丢失 + BufferTime: int64(bf), // 缓冲时间1天 缓冲时间内会获得新的token刷新令牌 此时一个用户会存在两个有效令牌 但是前端只留一个 另一个会丢失 StandardClaims: jwt.StandardClaims{ - NotBefore: time.Now().Unix() - 1000, // 签名生效时间 - ExpiresAt: time.Now().Unix() + global.GVA_CONFIG.JWT.ExpiresTime, // 过期时间 7天 配置文件 - Issuer: global.GVA_CONFIG.JWT.Issuer, // 签名的发行者 + NotBefore: time.Now().Unix() - 1000, // 签名生效时间 + ExpiresAt: time.Now().Add(ep).Unix(), // 过期时间 7天 配置文件 + Issuer: global.GVA_CONFIG.JWT.Issuer, // 签名的发行者 }, } return claims