From 69e3afc7707d467b758858b52d3784947f7a502b Mon Sep 17 00:00:00 2001
From: 疯狂的狮子Li <15040126243@163.com>
Date: 星期一, 20 五月 2024 10:25:23 +0800
Subject: [PATCH] !538 ♥️发布 5.2.0-BETA 公测版本 Merge pull request !538 from 疯狂的狮子Li/dev
---
ruoyi-common/ruoyi-common-security/src/main/java/org/dromara/common/security/config/SecurityConfig.java | 56
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/BusinessStatusEnum.java | 152
ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/interceptor/PlusDataPermissionInterceptor.java | 54
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfCategoryService.java | 51
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfDefinitionConfigService.java | 83
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfTaskBackNodeMapper.java | 13
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictTypeServiceImpl.java | 22
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfFormManageVo.java | 63
ruoyi-modules/ruoyi-generator/src/main/java/org/dromara/generator/domain/GenTableColumn.java | 16
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowProcessEventHandler.java | 20
ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/service.java.vm | 29
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysPostVo.java | 28
script/bin/ry.bat | 2
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/DeleteSequenceMultiInstanceCmd.java | 82
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/constant/CacheNames.java | 5
ruoyi-extend/ruoyi-snailjob-server/src/main/resources/logback-plus.xml | 92
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/regex/RegexValidator.java | 105
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysPostBo.java | 18
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysNoticeServiceImpl.java | 3
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowTaskEventHandler.java | 19
ruoyi-admin/src/main/java/org/dromara/web/listener/UserActionListener.java | 31
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/CompleteTaskBo.java | 65
ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/config/TenantConfig.java | 37
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfTaskBackNodeMapper.xml | 7
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfNodeConfigMapper.xml | 7
.run/ruoyi-snailjob-server.run.xml | 6
ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/interceptor/PlusWebInvokeTimeInterceptor.java | 17
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActTaskController.java | 295
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfDefinitionConfigMapper.xml | 7
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/MessageTypeEnum.java | 51
ruoyi-admin/src/main/java/org/dromara/web/service/impl/EmailAuthStrategy.java | 9
ruoyi-admin/Dockerfile | 4
script/docker/nginx/conf/nginx.conf | 16
ruoyi-common/ruoyi-common-redis/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports | 1
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/StartProcessBo.java | 49
script/sql/update/oracle/update_5.1.0-5.1.1.sql | 4
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActModelController.java | 147
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/CustomDefaultProcessDiagramCanvas.java | 108
ruoyi-admin/src/main/resources/application-prod.yml | 92
script/sql/update/sqlserver/update_5.1.2-5.2.0.sql | 29
ruoyi-extend/ruoyi-snailjob-server/src/main/java/org/dromara/snailjob/SnailJobServerApplication.java | 19
ruoyi-common/ruoyi-common-redis/pom.xml | 10
ruoyi-admin/src/main/resources/application-dev.yml | 93
ruoyi-extend/ruoyi-monitor-admin/src/main/java/org/dromara/monitor/admin/config/AdminServerConfig.java | 4
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/DelegateBo.java | 38
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActHiTaskinstMapper.java | 16
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysOssConfig.java | 2
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/ExecutionChildByExecutionIdCmd.java | 39
ruoyi-common/ruoyi-common-oss/pom.xml | 40
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActProcessInstanceController.java | 160
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysRoleService.java | 17
pom.xml | 95
ruoyi-modules/pom.xml | 1
ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/UndertowConfig.java | 8
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysSocialService.java | 6
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestCustomProcessHandler.java | 31
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/FormTypeEnum.java | 54
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ActHistoryInfoVo.java | 89
ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysUserMapper.xml | 104
ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/topiam/AuthTopIamRequest.java | 100
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserVo.java | 5
ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/utils/SocialUtils.java | 5
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessInvalidBo.java | 31
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfNodeConfigServiceImpl.java | 75
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysSocialServiceImpl.java | 10
ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/config/EncryptorAutoConfiguration.java | 14
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfFormManageController.java | 114
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestLeaveTaskListener.java | 21
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfCopy.java | 29
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/model/LoginUser.java | 6
script/sql/update/sqlserver/update_5.0-5.1.sql | 2
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysUserOnline.java | 1
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/BackProcessBo.java | 44
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/regex/RegexUtils.java | 30
ruoyi-admin/src/main/java/org/dromara/web/service/SysRegisterService.java | 6
ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application-dev.yml | 47
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDeptService.java | 16
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfDefinitionConfigServiceImpl.java | 117
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessInstanceBo.java | 43
ruoyi-common/ruoyi-common-mybatis/pom.xml | 13
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/AddMultiBo.java | 40
ruoyi-common/ruoyi-common-job/src/main/java/org/dromara/common/job/config/SnailJobConfig.java | 37
ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/page/PageQuery.java | 4
ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/config/RedisConfig.java | 34
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessDefinitionBo.java | 34
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/ValidatorUtils.java | 13
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/TestLeaveVo.java | 70
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfNodeConfig.java | 61
ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application.yml | 39
.run/ruoyi-server.run.xml | 2
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/constant/RegexConstants.java | 54
ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/handler/RedisExceptionHandler.java | 30
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysMenuBo.java | 4
ruoyi-admin/src/main/java/org/dromara/web/controller/CaptchaController.java | 14
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActHiTaskinstService.java | 11
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfDefinitionConfigController.java | 79
ruoyi-common/ruoyi-common-log/src/main/java/org/dromara/common/log/aspect/LogAspect.java | 31
ruoyi-common/ruoyi-common-ratelimiter/src/main/resources/spel-extension.json | 7
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/TaskStatusEnum.java | 94
ruoyi-common/ruoyi-common-satoken/pom.xml | 5
script/sql/oracle/oracle_ry_vue_5.X.sql | 344
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/AddSequenceMultiInstanceCmd.java | 61
ruoyi-common/ruoyi-common-sms/src/main/java/org/dromara/common/sms/core/dao/PlusSmsDao.java | 72
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/TestLeaveMapper.java | 15
script/sql/postgres/flowable.sql | 341
ruoyi-admin/src/main/java/org/dromara/web/controller/AuthController.java | 10
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/UserDTO.java | 73
ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/utils/RedisUtils.java | 12
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/WorkflowUtils.java | 343
script/sql/sqlserver/snail_job_sqlserver.sql | 2697 ++++++
ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application-prod.yml | 47
ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/config/MybatisPlusConfig.java | 35
ruoyi-admin/src/main/java/org/dromara/web/service/IAuthStrategy.java | 14
script/sql/snail_job.sql | 509 +
ruoyi-common/ruoyi-common-encrypt/pom.xml | 17
script/sql/update/update_5.1.1-5.1.2.sql | 1
ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisDecryptInterceptor.java | 4
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/CustomDefaultProcessDiagramGenerator.java | 1120 ++
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestCustomTaskHandler.java | 23
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfFormManageMapper.java | 15
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfFormManageServiceImpl.java | 111
ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysPostMapper.xml | 23
ruoyi-common/ruoyi-common-bom/pom.xml | 2
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfCategoryServiceImpl.java | 129
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysLogininforServiceImpl.java | 23
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/monitor/SysUserOnlineController.java | 40
ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/PlusDataPermissionHandler.java | 83
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysPostServiceImpl.java | 69
ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/package-info.java | 5
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfTaskBackNodeServiceImpl.java | 141
ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/handler/SaTokenExceptionHandler.java | 52
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysClientController.java | 2
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfCategoryMapper.java | 15
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TransmitBo.java | 37
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/UserService.java | 45
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/handler/TaskTimeoutJobHandler.java | 38
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/TestLeaveController.java | 106
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActTaskMapper.xml | 78
script/sql/ry_vue_5.X.sql | 331
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/constant/FlowConstant.java | 137
ruoyi-common/ruoyi-common-job/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports | 1
ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/factory/OssFactory.java | 29
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/StringUtils.java | 2
ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/snailjob/TestClassJobExecutor.java | 19
ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/config/CacheConfig.java | 45
ruoyi-modules/ruoyi-workflow/pom.xml | 116
script/sql/oracle/flowable.sql | 259
script/bin/ry.sh | 2
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysProfileController.java | 5
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/OssDTO.java | 46
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActProcessDefinitionServiceImpl.java | 438 +
ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/snailjob/TestAnnoJobExecutor.java | 23
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysPost.java | 10
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ModelVo.java | 48
ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/topiam/AuthTopiamSource.java | 51
ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/manager/PlusSpringCacheManager.java | 4
ruoyi-extend/ruoyi-snailjob-server/Dockerfile | 19
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfNodeConfigService.java | 56
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfCategory.java | 52
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/UpdateBusinessStatusCmd.java | 37
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysClientServiceImpl.java | 15
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfTaskBackNodeService.java | 65
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfFormManage.java | 51
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfFormManageBo.java | 53
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActHiTaskinstMapper.xml | 7
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysDeptMapper.java | 2
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictDataServiceImpl.java | 18
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfCategoryVo.java | 58
ruoyi-modules/ruoyi-generator/src/main/resources/mapper/generator/GenTableMapper.xml | 38
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/RoleDTO.java | 4
ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/handle/TenantKeyPrefixHandler.java | 7
ruoyi-common/ruoyi-common-translation/src/main/java/org/dromara/common/translation/core/impl/NicknameTranslationImpl.java | 4
script/sql/update/postgres/update_5.0-5.1.sql | 2
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActHiProcinstService.java | 31
ruoyi-common/ruoyi-common-web/pom.xml | 5
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysDeptVo.java | 6
ruoyi-admin/src/main/resources/application.yml | 32
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDictDataController.java | 6
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/annotation/FlowListenerAnnotation.java | 27
ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisEncryptInterceptor.java | 4
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfFormManageMapper.xml | 7
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActProcessDefinitionService.java | 91
ruoyi-extend/ruoyi-monitor-admin/Dockerfile | 5
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ModelBo.java | 66
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/exception/ServiceException.java | 13
ruoyi-admin/src/main/java/org/dromara/web/service/impl/XcxAuthStrategy.java | 5
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfDefinitionConfigBo.java | 59
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/ActHiProcinst.java | 152
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/TaskVo.java | 173
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysDept.java | 7
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysUserMapper.java | 47
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDeptBo.java | 6
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/AsyncConfig.java | 8
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysRoleMapper.java | 15
ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/controller.java.vm | 4
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/factory/RegexPatternPoolFactory.java | 52
ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/InjectionMetaObjectHandler.java | 28
ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/CellMergeStrategy.java | 82
script/sql/update/postgres/update_5.1.1-5.1.2.sql | 1
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfCategoryBo.java | 54
ruoyi-admin/src/main/java/org/dromara/web/service/impl/SocialAuthStrategy.java | 25
ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/serviceImpl.java.vm | 30
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/ActHiTaskinst.java | 193
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDeptServiceImpl.java | 29
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TaskBo.java | 33
ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/mapper/BaseMapperPlus.java | 14
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfNodeConfigBo.java | 63
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysPostService.java | 8
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfDefinitionConfigMapper.java | 15
script/sql/update/oracle/update_5.0-5.1.sql | 2
ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/EncryptResponseBodyWrapper.java | 1
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/SysUserMultiBo.java | 39
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowEventStrategy.java | 73
ruoyi-common/ruoyi-common-tenant/pom.xml | 6
ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index-tree.vue.vm | 77
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActProcessInstanceService.java | 118
ruoyi-common/ruoyi-common-sms/pom.xml | 13
ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/CryptoFilter.java | 54
ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialProperties.java | 5
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActModelServiceImpl.java | 424 +
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysPostMapper.java | 22
ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/annotation/CellMerge.java | 5
ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/manager/CaffeineCacheDecorator.java | 90
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActProcessDefinitionController.java | 147
ruoyi-common/ruoyi-common-json/src/main/java/org/dromara/common/json/utils/JsonUtils.java | 61
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/AttachmentCmd.java | 64
script/sql/update/oracle/update_5.1.1-5.1.2.sql | 1
script/docker/docker-compose.yml | 20
ruoyi-common/ruoyi-common-ratelimiter/src/main/java/org/dromara/common/ratelimiter/aspectj/RateLimiterAspect.java | 76
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysUserServiceImpl.java | 227
ruoyi-common/ruoyi-common-mybatis/src/main/resources/spy.properties | 8
script/sql/sqlserver/sqlserver_ry_vue_5.X.sql | 709 +
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/TestLeave.java | 58
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActTaskServiceImpl.java | 872 ++
script/sql/flowable.sql | 175
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActModelService.java | 83
ruoyi-extend/ruoyi-snailjob-server/pom.xml | 46
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/package-info.md | 3
script/sql/postgres/postgres_ry_vue_5.X.sql | 363
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfDefinitionConfig.java | 56
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDictTypeBo.java | 3
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/SpringUtils.java | 6
ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/CaptchaConfig.java | 2
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysUserController.java | 36
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActHiProcinstMapper.java | 16
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysOssConfigBo.java | 4
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ParticipantVo.java | 43
ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/core/OssClient.java | 649 +
ruoyi-common/ruoyi-common-security/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports | 1
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysRoleController.java | 6
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfCategoryMapper.xml | 7
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysSocialBo.java | 6
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ProcessInstanceVo.java | 100
script/sql/sqlserver/flowable.sql | 447 +
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActTaskMapper.java | 47
ruoyi-extend/ruoyi-snailjob-server/src/main/resources/banner.txt | 11
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/DeleteMultiBo.java | 52
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysOssConfigVo.java | 2
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDictDataService.java | 9
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfFormManageService.java | 81
ruoyi-admin/src/main/resources/ip2region.xdb | 0
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TaskUrgingBo.java | 34
ruoyi-common/ruoyi-common-log/pom.xml | 5
ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/ResourcesConfig.java | 9
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TerminationBo.java | 31
.run/ruoyi-monitor-admin.run.xml | 2
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestLeaveExecutionListener.java | 28
ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialLoginConfigProperties.java | 7
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssConfigService.java | 7
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysOssServiceImpl.java | 96
ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysRoleMapper.xml | 16
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/UpdateHiTaskInstCmd.java | 51
ruoyi-admin/src/main/java/org/dromara/web/service/SysLoginService.java | 42
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/QueryUtils.java | 154
README.md | 10
ruoyi-extend/pom.xml | 2
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserExportVo.java | 3
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActHiProcinstMapper.xml | 7
ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/config/SaTokenConfig.java | 9
ruoyi-modules/ruoyi-demo/src/main/java/org/dromara/demo/controller/SmsController.java | 30
ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/core/EncryptorManager.java | 96
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfNodeConfigMapper.java | 15
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActHiTaskinstServiceImpl.java | 18
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfNodeConfigVo.java | 75
ruoyi-common/ruoyi-common-sms/src/main/java/org/dromara/common/sms/config/SmsAutoConfiguration.java | 18
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/config/GlobalFlowableListener.java | 139
ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysDeptMapper.xml | 13
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActProcessInstanceServiceImpl.java | 683 +
ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/core/dao/PlusSaTokenDao.java | 35
ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/ExcelDownHandler.java | 8
ruoyi-common/ruoyi-common-idempotent/src/main/java/org/dromara/common/idempotent/aspectj/RepeatSubmitAspect.java | 16
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/ModelUtils.java | 289
script/sql/update/update_5.1.2-5.2.0.sql | 5
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysPostController.java | 26
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysUserService.java | 24
ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index.vue.vm | 91
script/sql/update/oracle/update_5.1.2-5.2.0.sql | 9
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/TestLeaveServiceImpl.java | 121
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TestLeaveBo.java | 75
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfTaskBackNode.java | 61
ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/handler/GlobalExceptionHandler.java | 48
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssService.java | 44
script/bpmn/模型.zip | 0
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/DeleteExecutionCmd.java | 36
ruoyi-admin/pom.xml | 21
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysClientService.java | 4
ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/utils/LoginHelper.java | 96
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/MultiInstanceVo.java | 33
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfDefinitionConfigVo.java | 70
ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/entity/UploadResult.java | 6
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDeptController.java | 18
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/VariableVo.java | 28
ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/TestLeaveMapper.xml | 7
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/GraphicInfoVo.java | 47
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActTaskService.java | 161
ruoyi-common/ruoyi-common-job/pom.xml | 16
/dev/null | 175
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/ITestLeaveService.java | 49
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfCategoryController.java | 106
script/sql/update/postgres/update_5.1.2-5.2.0.sql | 9
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActHiProcinstServiceImpl.java | 51
ruoyi-admin/src/main/java/org/dromara/web/domain/vo/TenantListVo.java | 9
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysConfigServiceImpl.java | 1
script/sql/postgres/snail_job_postgre.sql | 825 +
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/OssService.java | 11
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ProcessDefinitionVo.java | 70
ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/config/FlowableConfig.java | 32
ruoyi-admin/src/main/java/org/dromara/web/service/impl/PasswordAuthStrategy.java | 9
ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/MybatisExceptionHandler.java | 3
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysUserBo.java | 5
ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysRoleServiceImpl.java | 28
ruoyi-common/ruoyi-common-core/pom.xml | 5
script/sql/oracle/snail_job_oracle.sql | 894 ++
ruoyi-admin/src/main/java/org/dromara/web/service/impl/SmsAuthStrategy.java | 9
ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/ApplicationConfig.java | 2
ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/enumd/AccessPolicyType.java | 18
336 files changed, 22,890 insertions(+), 2,157 deletions(-)
diff --git a/.run/ruoyi-monitor-admin.run.xml b/.run/ruoyi-monitor-admin.run.xml
index 4837d6a..095b3d7 100644
--- a/.run/ruoyi-monitor-admin.run.xml
+++ b/.run/ruoyi-monitor-admin.run.xml
@@ -2,7 +2,7 @@
<configuration default="false" name="ruoyi-monitor-admin" type="docker-deploy" factoryName="dockerfile" server-name="Docker">
<deployment type="dockerfile">
<settings>
- <option name="imageTag" value="ruoyi/ruoyi-monitor-admin:5.1.2" />
+ <option name="imageTag" value="ruoyi/ruoyi-monitor-admin:5.2.0" />
<option name="buildOnly" value="true" />
<option name="sourceFilePath" value="ruoyi-extend/ruoyi-monitor-admin/Dockerfile" />
</settings>
diff --git a/.run/ruoyi-server.run.xml b/.run/ruoyi-server.run.xml
index a29ff2a..0463c34 100644
--- a/.run/ruoyi-server.run.xml
+++ b/.run/ruoyi-server.run.xml
@@ -2,7 +2,7 @@
<configuration default="false" name="ruoyi-server" type="docker-deploy" factoryName="dockerfile" server-name="Docker">
<deployment type="dockerfile">
<settings>
- <option name="imageTag" value="ruoyi/ruoyi-server:5.1.2" />
+ <option name="imageTag" value="ruoyi/ruoyi-server:5.2.0" />
<option name="buildOnly" value="true" />
<option name="sourceFilePath" value="ruoyi-admin/Dockerfile" />
</settings>
diff --git a/.run/ruoyi-powerjob-server.run.xml b/.run/ruoyi-snailjob-server.run.xml
similarity index 68%
rename from .run/ruoyi-powerjob-server.run.xml
rename to .run/ruoyi-snailjob-server.run.xml
index 77a4af0..761915e 100644
--- a/.run/ruoyi-powerjob-server.run.xml
+++ b/.run/ruoyi-snailjob-server.run.xml
@@ -1,10 +1,10 @@
<component name="ProjectRunConfigurationManager">
- <configuration default="false" name="ruoyi-powerjob-server" type="docker-deploy" factoryName="dockerfile" server-name="Docker">
+ <configuration default="false" name="ruoyi-snailjob-server" type="docker-deploy" factoryName="dockerfile" server-name="Docker">
<deployment type="dockerfile">
<settings>
- <option name="imageTag" value="ruoyi/ruoyi-powerjob-server:5.1.2" />
+ <option name="imageTag" value="ruoyi/ruoyi-snailjob-server:5.2.0" />
<option name="buildOnly" value="true" />
- <option name="sourceFilePath" value="ruoyi-extend/ruoyi-powerjob-server/Dockerfile" />
+ <option name="sourceFilePath" value="ruoyi-extend/ruoyi-snailjob-server/Dockerfile" />
</settings>
</deployment>
<method v="2" />
diff --git a/README.md b/README.md
index a542b47..05dd679 100644
--- a/README.md
+++ b/README.md
@@ -9,7 +9,7 @@
[](https://gitee.com/dromara/RuoYi-Vue-Plus/blob/master/LICENSE)
[
<br>
-[](https://gitee.com/dromara/RuoYi-Vue-Plus)
+[](https://gitee.com/dromara/RuoYi-Vue-Plus)
[]()
[]()
[]()
@@ -27,8 +27,10 @@
## 璧炲姪鍟�
-MaxKey - https://gitee.com/dromara/MaxKey <br>
-CCFlow - https://gitee.com/opencc/RuoYi-JFlow <br>
+MaxKey 涓氱晫棰嗗厛鍗曠偣鐧诲綍浜у搧 - https://gitee.com/dromara/MaxKey <br>
+CCFlow 椹拌仒浣庝唬鐮�-娴佺▼-琛ㄥ崟 - https://gitee.com/opencc/RuoYi-JFlow <br>
+鏁拌埖绉戞妧 杞欢瀹氬埗寮�鍙慉PP灏忕▼搴忕瓑 - http://www.shuduokeji.com/ <br>
+寮曡繄淇℃伅 杞欢寮�鍙戝钩鍙� - https://www.jnpfsoft.com/index.html?from=plus-doc <br>
[濡備綍鎴愪负璧炲姪鍟� 鍔犵兢鑱旂郴浣滆�呰璋圿(https://plus-doc.dromara.org/#/common/add_group)
# 鏈鏋朵笌RuoYi鐨勫姛鑳藉樊寮�
@@ -62,7 +64,7 @@
| 搴忓垪鍖� | 閲囩敤 Jackson Spring瀹樻柟鍐呯疆搴忓垪鍖� 闈犺氨!!! | 閲囩敤 fastjson bugjson 杩滆繎闂诲悕 |
| 鍒嗗竷寮忓箓绛� | 鍙傝�冪編鍥TIS闃查噸绯荤粺绠�鍖栧疄鐜�(缁嗚妭鍙湅鏂囨。) | 鎵嬪姩缂栧啓娉ㄨВ鍩轰簬aop瀹炵幇 |
| 鍒嗗竷寮忛攣 | 閲囩敤 Lock4j 搴曞眰鍩轰簬 Redisson | 鏃� |
-| 鍒嗗竷寮忎换鍔¤皟搴� | 閲囩敤 PowerJob 澶╃敓鏀寔鍒嗗竷寮� 缁熶竴鐨勭鐞嗕腑蹇� | 閲囩敤 Quartz 鍩轰簬鏁版嵁搴撻攣鎬ц兘宸� 闆嗙兢闇�瑕佸仛寰堝閰嶇疆涓庢敼閫� |
+| 鍒嗗竷寮忎换鍔¤皟搴� | 閲囩敤 SnailJob 澶╃敓鏀寔鍒嗗竷寮� 缁熶竴鐨勭鐞嗕腑蹇� 鏀寔澶氱鏁版嵁搴� 鏀寔鍒嗙墖閲嶈瘯DAG浠诲姟娴佺瓑 | 閲囩敤 Quartz 鍩轰簬鏁版嵁搴撻攣鎬ц兘宸� 闆嗙兢闇�瑕佸仛寰堝閰嶇疆涓庢敼閫� |
| 鏂囦欢瀛樺偍 | 閲囩敤 Minio 鍒嗗竷寮忔枃浠跺瓨鍌� 澶╃敓鏀寔澶氭満銆佸纭洏銆佸鍒嗙墖銆佸鍓湰瀛樺偍<br/>鏀寔鏉冮檺绠$悊 瀹夊叏鍙潬 鏂囦欢鍙姞瀵嗗瓨鍌� | 閲囩敤 鏈満鏂囦欢瀛樺偍 鏂囦欢瑁告紡 鏄撲涪澶辨硠婕� 涓嶆敮鎸侀泦缇ゆ湁鍗曠偣鏁堝簲 |
| 浜戝瓨鍌� | 閲囩敤 AWS S3 鍗忚瀹㈡埛绔� 鏀寔 涓冪墰銆侀樋閲屻�佽吘璁� 绛変竴鍒囨敮鎸丼3鍗忚鐨勫巶瀹� | 涓嶆敮鎸� |
| 鐭俊 | 閲囩敤 sms4j 鐭俊铻嶅悎鍖� 鏀寔鏁板崄绉嶇煭淇″巶瀹� 鍙渶鍦▂ml閰嶇疆濂藉巶瀹跺瘑閽ュ嵆鍙娇鐢� 鍙鍘傚鍏辩敤 | 涓嶆敮鎸� |
diff --git a/pom.xml b/pom.xml
index 3aafe14..4d04d39 100644
--- a/pom.xml
+++ b/pom.xml
@@ -13,40 +13,41 @@
<description>RuoYi-Vue-Plus澶氱鎴风鐞嗙郴缁�</description>
<properties>
- <revision>5.1.2</revision>
- <spring-boot.version>3.1.7</spring-boot.version>
+ <revision>5.2.0-BETA</revision>
+ <spring-boot.version>3.2.5</spring-boot.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>17</java.version>
- <spring-boot.mybatis>3.0.3</spring-boot.mybatis>
- <springdoc.version>2.2.0</springdoc.version>
+ <mybatis.version>3.5.16</mybatis.version>
+ <springdoc.version>2.5.0</springdoc.version>
<therapi-javadoc.version>0.15.0</therapi-javadoc.version>
<poi.version>5.2.3</poi.version>
- <easyexcel.version>3.3.3</easyexcel.version>
+ <easyexcel.version>3.3.4</easyexcel.version>
<velocity.version>2.3</velocity.version>
- <satoken.version>1.37.0</satoken.version>
- <mybatis-plus.version>3.5.4</mybatis-plus.version>
+ <satoken.version>1.38.0</satoken.version>
+ <mybatis-plus.version>3.5.6</mybatis-plus.version>
<p6spy.version>3.9.1</p6spy.version>
- <hutool.version>5.8.22</hutool.version>
+ <hutool.version>5.8.27</hutool.version>
<okhttp.version>4.10.0</okhttp.version>
- <spring-boot-admin.version>3.1.8</spring-boot-admin.version>
- <redisson.version>3.24.3</redisson.version>
- <lock4j.version>2.2.5</lock4j.version>
- <dynamic-ds.version>4.2.0</dynamic-ds.version>
+ <spring-boot-admin.version>3.2.3</spring-boot-admin.version>
+ <redisson.version>3.29.0</redisson.version>
+ <lock4j.version>2.2.7</lock4j.version>
+ <dynamic-ds.version>4.3.0</dynamic-ds.version>
<alibaba-ttl.version>2.14.4</alibaba-ttl.version>
- <powerjob.version>4.3.6</powerjob.version>
- <mapstruct-plus.version>1.3.5</mapstruct-plus.version>
+ <snailjob.version>1.0.0-beta1</snailjob.version>
+ <mapstruct-plus.version>1.3.6</mapstruct-plus.version>
<mapstruct-plus.lombok.version>0.2.0</mapstruct-plus.lombok.version>
- <lombok.version>1.18.30</lombok.version>
+ <lombok.version>1.18.32</lombok.version>
<bouncycastle.version>1.76</bouncycastle.version>
<justauth.version>1.16.6</justauth.version>
<!-- 绂荤嚎IP鍦板潃瀹氫綅搴� -->
<ip2region.version>2.7.0</ip2region.version>
<!-- OSS 閰嶇疆 -->
- <aws-java-sdk-s3.version>1.12.600</aws-java-sdk-s3.version>
+ <aws.sdk.version>2.25.15</aws.sdk.version>
+ <aws.crt.version>0.29.13</aws.crt.version>
<!-- SMS 閰嶇疆 -->
- <sms4j.version>2.2.0</sms4j.version>
+ <sms4j.version>3.2.1</sms4j.version>
<!-- 闄愬埗妗嗘灦涓殑fastjson鐗堟湰 -->
<fastjson.version>1.2.83</fastjson.version>
@@ -56,6 +57,9 @@
<maven-compiler-plugin.verison>3.11.0</maven-compiler-plugin.verison>
<maven-surefire-plugin.version>3.1.2</maven-surefire-plugin.version>
<flatten-maven-plugin.version>1.3.0</flatten-maven-plugin.version>
+
+ <!--宸ヤ綔娴侀厤缃�-->
+ <flowable.version>7.0.0</flowable.version>
</properties>
<profiles>
@@ -106,6 +110,14 @@
<groupId>cn.hutool</groupId>
<artifactId>hutool-bom</artifactId>
<version>${hutool.version}</version>
+ <type>pom</type>
+ <scope>import</scope>
+ </dependency>
+
+ <dependency>
+ <groupId>org.flowable</groupId>
+ <artifactId>flowable-bom</artifactId>
+ <version>${flowable.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
@@ -205,14 +217,14 @@
</dependency>
<dependency>
- <groupId>org.mybatis.spring.boot</groupId>
- <artifactId>mybatis-spring-boot-starter</artifactId>
- <version>${spring-boot.mybatis}</version>
+ <groupId>org.mybatis</groupId>
+ <artifactId>mybatis</artifactId>
+ <version>${mybatis.version}</version>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
- <artifactId>mybatis-plus-boot-starter</artifactId>
+ <artifactId>mybatis-plus-spring-boot3-starter</artifactId>
<version>${mybatis-plus.version}</version>
</dependency>
@@ -235,10 +247,23 @@
<version>${okhttp.version}</version>
</dependency>
+ <!-- AWS SDK for Java 2.x -->
<dependency>
- <groupId>com.amazonaws</groupId>
- <artifactId>aws-java-sdk-s3</artifactId>
- <version>${aws-java-sdk-s3.version}</version>
+ <groupId>software.amazon.awssdk</groupId>
+ <artifactId>s3</artifactId>
+ <version>${aws.sdk.version}</version>
+ </dependency>
+ <!-- 浣跨敤AWS鍩轰簬 CRT 鐨� S3 瀹㈡埛绔� -->
+ <dependency>
+ <groupId>software.amazon.awssdk.crt</groupId>
+ <artifactId>aws-crt</artifactId>
+ <version>${aws.crt.version}</version>
+ </dependency>
+ <!-- 鍩轰簬 AWS CRT 鐨� S3 瀹㈡埛绔殑鎬ц兘澧炲己鐨� S3 浼犺緭绠$悊鍣� -->
+ <dependency>
+ <groupId>software.amazon.awssdk</groupId>
+ <artifactId>s3-transfer-manager</artifactId>
+ <version>${aws.sdk.version}</version>
</dependency>
<!--鐭俊sms4j-->
<dependency>
@@ -271,16 +296,16 @@
<version>${lock4j.version}</version>
</dependency>
- <!-- PowerJob -->
+ <!-- SnailJob Client -->
<dependency>
- <groupId>tech.powerjob</groupId>
- <artifactId>powerjob-worker-spring-boot-starter</artifactId>
- <version>${powerjob.version}</version>
+ <groupId>com.aizuda</groupId>
+ <artifactId>snail-job-client-starter</artifactId>
+ <version>${snailjob.version}</version>
</dependency>
<dependency>
- <groupId>tech.powerjob</groupId>
- <artifactId>powerjob-official-processors</artifactId>
- <version>${powerjob.version}</version>
+ <groupId>com.aizuda</groupId>
+ <artifactId>snail-job-client-job-core</artifactId>
+ <version>${snailjob.version}</version>
</dependency>
<dependency>
@@ -336,6 +361,13 @@
<dependency>
<groupId>org.dromara</groupId>
<artifactId>ruoyi-demo</artifactId>
+ <version>${revision}</version>
+ </dependency>
+
+ <!-- 宸ヤ綔娴佹ā鍧� -->
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-workflow</artifactId>
<version>${revision}</version>
</dependency>
@@ -398,6 +430,7 @@
<artifactId>maven-surefire-plugin</artifactId>
<version>${maven-surefire-plugin.version}</version>
<configuration>
+ <argLine>-Dfile.encoding=UTF-8</argLine>
<!-- 鏍规嵁鎵撳寘鐜鎵ц瀵瑰簲鐨凘Tag娴嬭瘯鏂规硶 -->
<groups>${profiles.active}</groups>
<!-- 鎺掗櫎鏍囩 -->
diff --git a/ruoyi-admin/Dockerfile b/ruoyi-admin/Dockerfile
index 4237ef9..609b04a 100644
--- a/ruoyi-admin/Dockerfile
+++ b/ruoyi-admin/Dockerfile
@@ -19,6 +19,6 @@
# 搴旂敤鍚嶇О 濡傛灉鎯冲尯鍒嗛泦缇よ妭鐐圭洃鎺� 鏀规垚涓嶅悓鐨勫悕绉板嵆鍙�
#-Dskywalking.agent.service_name=ruoyi-server \
#-javaagent:/ruoyi/skywalking/agent/skywalking-agent.jar \
- -jar app.jar \
- -XX:+HeapDumpOnOutOfMemoryError -Xlog:gc*,:time,tags,level -XX:+UseZGC ${JAVA_OPTS}
+ -XX:+HeapDumpOnOutOfMemoryError -XX:+UseZGC ${JAVA_OPTS} \
+ -jar app.jar
diff --git a/ruoyi-admin/pom.xml b/ruoyi-admin/pom.xml
index 26cd023..0ae1850 100644
--- a/ruoyi-admin/pom.xml
+++ b/ruoyi-admin/pom.xml
@@ -55,6 +55,11 @@
<dependency>
<groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-mail</artifactId>
+ </dependency>
+
+ <dependency>
+ <groupId>org.dromara</groupId>
<artifactId>ruoyi-system</artifactId>
</dependency>
@@ -75,6 +80,12 @@
<artifactId>ruoyi-demo</artifactId>
</dependency>
+ <!-- 宸ヤ綔娴佹ā鍧� -->
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-workflow</artifactId>
+ </dependency>
+
<dependency>
<groupId>de.codecentric</groupId>
<artifactId>spring-boot-admin-starter-client</artifactId>
@@ -91,6 +102,16 @@
<artifactId>JustAuth</artifactId>
</dependency>
+ <!-- SnailJob client -->
+ <dependency>
+ <groupId>com.aizuda</groupId>
+ <artifactId>snail-job-client-starter</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>com.aizuda</groupId>
+ <artifactId>snail-job-client-job-core</artifactId>
+ </dependency>
+
<!-- skywalking 鏁村悎 logback -->
<!-- <dependency>-->
<!-- <groupId>org.apache.skywalking</groupId>-->
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/controller/AuthController.java b/ruoyi-admin/src/main/java/org/dromara/web/controller/AuthController.java
index d0d7931..43e689b 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/controller/AuthController.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/controller/AuthController.java
@@ -23,9 +23,10 @@
import org.dromara.common.social.config.properties.SocialProperties;
import org.dromara.common.social.utils.SocialUtils;
import org.dromara.common.tenant.helper.TenantHelper;
+import org.dromara.common.websocket.dto.WebSocketMessageDto;
import org.dromara.common.websocket.utils.WebSocketUtils;
-import org.dromara.system.domain.SysClient;
import org.dromara.system.domain.bo.SysTenantBo;
+import org.dromara.system.domain.vo.SysClientVo;
import org.dromara.system.domain.vo.SysTenantVo;
import org.dromara.system.service.ISysClientService;
import org.dromara.system.service.ISysConfigService;
@@ -81,7 +82,7 @@
// 鎺堟潈绫诲瀷鍜屽鎴风id
String clientId = loginBody.getClientId();
String grantType = loginBody.getGrantType();
- SysClient client = clientService.queryByClientId(clientId);
+ SysClientVo client = clientService.queryByClientId(clientId);
// 鏌ヨ涓嶅埌 client 鎴� client 鍐呬笉鍖呭惈 grantType
if (ObjectUtil.isNull(client) || !StringUtils.contains(client.getGrantType(), grantType)) {
log.info("瀹㈡埛绔痠d: {} 璁よ瘉绫诲瀷锛歿} 寮傚父!.", clientId, grantType);
@@ -96,7 +97,10 @@
Long userId = LoginHelper.getUserId();
scheduledExecutorService.schedule(() -> {
- WebSocketUtils.sendMessage(userId, "娆㈣繋鐧诲綍RuoYi-Vue-Plus鍚庡彴绠$悊绯荤粺");
+ WebSocketMessageDto dto = new WebSocketMessageDto();
+ dto.setMessage("娆㈣繋鐧诲綍RuoYi-Vue-Plus鍚庡彴绠$悊绯荤粺");
+ dto.setSessionKeys(List.of(userId));
+ WebSocketUtils.publishMessage(dto);
}, 3, TimeUnit.SECONDS);
return R.ok(loginVo);
}
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/controller/CaptchaController.java b/ruoyi-admin/src/main/java/org/dromara/web/controller/CaptchaController.java
index ef33f5b..1a476a9 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/controller/CaptchaController.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/controller/CaptchaController.java
@@ -5,6 +5,9 @@
import cn.hutool.captcha.generator.CodeGenerator;
import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.RandomUtil;
+import jakarta.validation.constraints.NotBlank;
+import lombok.RequiredArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
import org.dromara.common.core.constant.Constants;
import org.dromara.common.core.constant.GlobalConstants;
import org.dromara.common.core.domain.R;
@@ -21,11 +24,7 @@
import org.dromara.sms4j.api.SmsBlend;
import org.dromara.sms4j.api.entity.SmsResponse;
import org.dromara.sms4j.core.factory.SmsFactory;
-import org.dromara.sms4j.provider.enumerate.SupplierType;
import org.dromara.web.domain.vo.CaptchaVo;
-import jakarta.validation.constraints.NotBlank;
-import lombok.RequiredArgsConstructor;
-import lombok.extern.slf4j.Slf4j;
import org.springframework.expression.Expression;
import org.springframework.expression.ExpressionParser;
import org.springframework.expression.spel.standard.SpelExpressionParser;
@@ -66,11 +65,11 @@
String templateId = "";
LinkedHashMap<String, String> map = new LinkedHashMap<>(1);
map.put("code", code);
- SmsBlend smsBlend = SmsFactory.createSmsBlend(SupplierType.ALIBABA);
+ SmsBlend smsBlend = SmsFactory.getSmsBlend("config1");
SmsResponse smsResponse = smsBlend.sendMessage(phonenumber, templateId, map);
- if (!"OK".equals(smsResponse.getCode())) {
+ if (!smsResponse.isSuccess()) {
log.error("楠岃瘉鐮佺煭淇″彂閫佸紓甯� => {}", smsResponse);
- return R.fail(smsResponse.getMessage());
+ return R.fail(smsResponse.getData().toString());
}
return R.ok();
}
@@ -121,6 +120,7 @@
AbstractCaptcha captcha = SpringUtils.getBean(captchaProperties.getCategory().getClazz());
captcha.setGenerator(codeGenerator);
captcha.createCode();
+ // 濡傛灉鏄暟瀛﹂獙璇佺爜锛屼娇鐢⊿pEL琛ㄨ揪寮忓鐞嗛獙璇佺爜缁撴灉
String code = captcha.getCode();
if (isMath) {
ExpressionParser parser = new SpelExpressionParser();
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/domain/vo/TenantListVo.java b/ruoyi-admin/src/main/java/org/dromara/web/domain/vo/TenantListVo.java
index 4d4bc89..db9c271 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/domain/vo/TenantListVo.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/domain/vo/TenantListVo.java
@@ -13,10 +13,19 @@
@AutoMapper(target = SysTenantVo.class)
public class TenantListVo {
+ /**
+ * 绉熸埛缂栧彿
+ */
private String tenantId;
+ /**
+ * 浼佷笟鍚嶇О
+ */
private String companyName;
+ /**
+ * 鍩熷悕
+ */
private String domain;
}
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/listener/UserActionListener.java b/ruoyi-admin/src/main/java/org/dromara/web/listener/UserActionListener.java
index 6d67fb1..a472404 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/listener/UserActionListener.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/listener/UserActionListener.java
@@ -10,7 +10,6 @@
import org.dromara.common.core.constant.CacheConstants;
import org.dromara.common.core.constant.Constants;
import org.dromara.common.core.domain.dto.UserOnlineDTO;
-import org.dromara.common.core.domain.model.LoginUser;
import org.dromara.common.core.utils.MessageUtils;
import org.dromara.common.core.utils.ServletUtils;
import org.dromara.common.core.utils.SpringUtils;
@@ -18,6 +17,7 @@
import org.dromara.common.log.event.LogininforEvent;
import org.dromara.common.redis.utils.RedisUtils;
import org.dromara.common.satoken.utils.LoginHelper;
+import org.dromara.common.tenant.helper.TenantHelper;
import org.dromara.web.service.SysLoginService;
import org.springframework.stereotype.Component;
@@ -43,7 +43,6 @@
public void doLogin(String loginType, Object loginId, String tokenValue, SaLoginModel loginModel) {
UserAgent userAgent = UserAgentUtil.parse(ServletUtils.getRequest().getHeader("User-Agent"));
String ip = ServletUtils.getClientIP();
- LoginUser user = LoginHelper.getLoginUser();
UserOnlineDTO dto = new UserOnlineDTO();
dto.setIpaddr(ip);
dto.setLoginLocation(AddressUtils.getRealAddressByIP(ip));
@@ -51,25 +50,29 @@
dto.setOs(userAgent.getOs().getName());
dto.setLoginTime(System.currentTimeMillis());
dto.setTokenId(tokenValue);
- dto.setUserName(user.getUsername());
- dto.setClientKey(user.getClientKey());
- dto.setDeviceType(user.getDeviceType());
- dto.setDeptName(user.getDeptName());
- if(tokenConfig.getTimeout() == -1) {
- RedisUtils.setCacheObject(CacheConstants.ONLINE_TOKEN_KEY + tokenValue, dto);
- } else {
- RedisUtils.setCacheObject(CacheConstants.ONLINE_TOKEN_KEY + tokenValue, dto, Duration.ofSeconds(tokenConfig.getTimeout()));
- }
+ String username = (String) loginModel.getExtra(LoginHelper.USER_NAME_KEY);
+ String tenantId = (String) loginModel.getExtra(LoginHelper.TENANT_KEY);
+ dto.setUserName(username);
+ dto.setClientKey((String) loginModel.getExtra(LoginHelper.CLIENT_KEY));
+ dto.setDeviceType(loginModel.getDevice());
+ dto.setDeptName((String) loginModel.getExtra(LoginHelper.DEPT_NAME_KEY));
+ TenantHelper.dynamic(tenantId, () -> {
+ if(tokenConfig.getTimeout() == -1) {
+ RedisUtils.setCacheObject(CacheConstants.ONLINE_TOKEN_KEY + tokenValue, dto);
+ } else {
+ RedisUtils.setCacheObject(CacheConstants.ONLINE_TOKEN_KEY + tokenValue, dto, Duration.ofSeconds(tokenConfig.getTimeout()));
+ }
+ });
// 璁板綍鐧诲綍鏃ュ織
LogininforEvent logininforEvent = new LogininforEvent();
- logininforEvent.setTenantId(user.getTenantId());
- logininforEvent.setUsername(user.getUsername());
+ logininforEvent.setTenantId(tenantId);
+ logininforEvent.setUsername(username);
logininforEvent.setStatus(Constants.LOGIN_SUCCESS);
logininforEvent.setMessage(MessageUtils.message("user.login.success"));
logininforEvent.setRequest(ServletUtils.getRequest());
SpringUtils.context().publishEvent(logininforEvent);
// 鏇存柊鐧诲綍淇℃伅
- loginService.recordLoginInfo(user.getUserId(), ip);
+ loginService.recordLoginInfo((Long) loginModel.getExtra(LoginHelper.USER_KEY), ip);
log.info("user doLogin, userId:{}, token:{}", loginId, tokenValue);
}
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/service/IAuthStrategy.java b/ruoyi-admin/src/main/java/org/dromara/web/service/IAuthStrategy.java
index d4f9c73..a75b913 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/service/IAuthStrategy.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/service/IAuthStrategy.java
@@ -4,6 +4,7 @@
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.utils.SpringUtils;
import org.dromara.system.domain.SysClient;
+import org.dromara.system.domain.vo.SysClientVo;
import org.dromara.web.domain.vo.LoginVo;
/**
@@ -17,8 +18,13 @@
/**
* 鐧诲綍
+ *
+ * @param body 鐧诲綍瀵硅薄
+ * @param client 鎺堟潈绠$悊瑙嗗浘瀵硅薄
+ * @param grantType 鎺堟潈绫诲瀷
+ * @return 鐧诲綍楠岃瘉淇℃伅
*/
- static LoginVo login(String body, SysClient client, String grantType) {
+ static LoginVo login(String body, SysClientVo client, String grantType) {
// 鎺堟潈绫诲瀷鍜屽鎴风id
String beanName = grantType + BASE_NAME;
if (!SpringUtils.containsBean(beanName)) {
@@ -30,7 +36,11 @@
/**
* 鐧诲綍
+ *
+ * @param body 鐧诲綍瀵硅薄
+ * @param client 鎺堟潈绠$悊瑙嗗浘瀵硅薄
+ * @return 鐧诲綍楠岃瘉淇℃伅
*/
- LoginVo login(String body, SysClient client);
+ LoginVo login(String body, SysClientVo client);
}
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/service/SysLoginService.java b/ruoyi-admin/src/main/java/org/dromara/web/service/SysLoginService.java
index 37802b7..af6e7f5 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/service/SysLoginService.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/service/SysLoginService.java
@@ -5,6 +5,7 @@
import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.ObjectUtil;
+import com.baomidou.lock.annotation.Lock4j;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import me.zhyd.oauth.model.AuthUser;
@@ -15,6 +16,7 @@
import org.dromara.common.core.domain.model.LoginUser;
import org.dromara.common.core.enums.LoginType;
import org.dromara.common.core.enums.TenantStatus;
+import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.exception.user.UserException;
import org.dromara.common.core.utils.*;
import org.dromara.common.log.event.LogininforEvent;
@@ -25,13 +27,9 @@
import org.dromara.common.tenant.helper.TenantHelper;
import org.dromara.system.domain.SysUser;
import org.dromara.system.domain.bo.SysSocialBo;
-import org.dromara.system.domain.vo.SysSocialVo;
-import org.dromara.system.domain.vo.SysTenantVo;
-import org.dromara.system.domain.vo.SysUserVo;
+import org.dromara.system.domain.vo.*;
import org.dromara.system.mapper.SysUserMapper;
-import org.dromara.system.service.ISysPermissionService;
-import org.dromara.system.service.ISysSocialService;
-import org.dromara.system.service.ISysTenantService;
+import org.dromara.system.service.*;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
@@ -59,6 +57,8 @@
private final ISysTenantService tenantService;
private final ISysPermissionService permissionService;
private final ISysSocialService sysSocialService;
+ private final ISysRoleService roleService;
+ private final ISysDeptService deptService;
private final SysUserMapper userMapper;
@@ -66,20 +66,28 @@
* 缁戝畾绗笁鏂圭敤鎴�
*
* @param authUserData 鎺堟潈鍝嶅簲瀹炰綋
- * @return 缁熶竴鍝嶅簲瀹炰綋
*/
+ @Lock4j
public void socialRegister(AuthUser authUserData) {
String authId = authUserData.getSource() + authUserData.getUuid();
// 绗笁鏂圭敤鎴蜂俊鎭�
SysSocialBo bo = BeanUtil.toBean(authUserData, SysSocialBo.class);
BeanUtil.copyProperties(authUserData.getToken(), bo);
- bo.setUserId(LoginHelper.getUserId());
+ Long userId = LoginHelper.getUserId();
+ bo.setUserId(userId);
bo.setAuthId(authId);
bo.setOpenId(authUserData.getUuid());
bo.setUserName(authUserData.getUsername());
bo.setNickName(authUserData.getNickname());
+ List<SysSocialVo> checkList = sysSocialService.selectByAuthId(authId);
+ if (CollUtil.isNotEmpty(checkList)) {
+ throw new ServiceException("姝や笁鏂硅处鍙峰凡缁忚缁戝畾!");
+ }
// 鏌ヨ鏄惁宸茬粡缁戝畾鐢ㄦ埛
- List<SysSocialVo> list = sysSocialService.selectByAuthId(authId);
+ SysSocialBo params = new SysSocialBo();
+ params.setUserId(userId);
+ params.setSource(bo.getSource());
+ List<SysSocialVo> list = sysSocialService.queryList(params);
if (CollUtil.isEmpty(list)) {
// 娌℃湁缁戝畾鐢ㄦ埛, 鏂板鐢ㄦ埛淇℃伅
sysSocialService.insertByBo(bo);
@@ -87,6 +95,8 @@
// 鏇存柊鐢ㄦ埛淇℃伅
bo.setId(list.get(0).getId());
sysSocialService.updateByBo(bo);
+ // 濡傛灉瑕佺粦瀹氱殑骞冲彴璐﹀彿宸茬粡琚粦瀹氳繃浜� 鏄惁鎶涘紓甯歌嚜琛屽喅鏂�
+ // throw new ServiceException("姝ゅ钩鍙拌处鍙峰凡缁忚缁戝畾!");
}
}
@@ -132,7 +142,6 @@
SpringUtils.context().publishEvent(logininforEvent);
}
-
/**
* 鏋勫缓鐧诲綍鐢ㄦ埛
*/
@@ -146,9 +155,16 @@
loginUser.setUserType(user.getUserType());
loginUser.setMenuPermission(permissionService.getMenuPermission(user.getUserId()));
loginUser.setRolePermission(permissionService.getRolePermission(user.getUserId()));
- loginUser.setDeptName(ObjectUtil.isNull(user.getDept()) ? "" : user.getDept().getDeptName());
- List<RoleDTO> roles = BeanUtil.copyToList(user.getRoles(), RoleDTO.class);
- loginUser.setRoles(roles);
+ TenantHelper.dynamic(user.getTenantId(), () -> {
+ SysDeptVo dept = null;
+ if (ObjectUtil.isNotNull(user.getDeptId())) {
+ dept = deptService.selectDeptById(user.getDeptId());
+ }
+ loginUser.setDeptName(ObjectUtil.isNull(dept) ? "" : dept.getDeptName());
+ loginUser.setDeptCategory(ObjectUtil.isNull(dept) ? "" : dept.getDeptCategory());
+ List<SysRoleVo> roles = roleService.selectRolesByUserId(user.getUserId());
+ loginUser.setRoles(BeanUtil.copyToList(roles, RoleDTO.class));
+ });
return loginUser;
}
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/service/SysRegisterService.java b/ruoyi-admin/src/main/java/org/dromara/web/service/SysRegisterService.java
index f38d074..ddab279 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/service/SysRegisterService.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/service/SysRegisterService.java
@@ -1,7 +1,6 @@
package org.dromara.web.service;
import cn.dev33.satoken.secure.BCrypt;
-import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import lombok.RequiredArgsConstructor;
import org.dromara.common.core.constant.Constants;
@@ -61,8 +60,7 @@
boolean exist = TenantHelper.dynamic(tenantId, () -> {
return userMapper.exists(new LambdaQueryWrapper<SysUser>()
- .eq(SysUser::getUserName, sysUser.getUserName())
- .ne(ObjectUtil.isNotNull(sysUser.getUserId()), SysUser::getUserId, sysUser.getUserId()));
+ .eq(SysUser::getUserName, sysUser.getUserName()));
});
if (exist) {
throw new UserException("user.register.save.error", username);
@@ -82,7 +80,7 @@
* @param uuid 鍞竴鏍囪瘑
*/
public void validateCaptcha(String tenantId, String username, String code, String uuid) {
- String verifyKey = GlobalConstants.CAPTCHA_CODE_KEY + StringUtils.defaultString(uuid, "");
+ String verifyKey = GlobalConstants.CAPTCHA_CODE_KEY + StringUtils.blankToDefault(uuid, "");
String captcha = RedisUtils.getCacheObject(verifyKey);
RedisUtils.deleteObject(verifyKey);
if (captcha == null) {
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/EmailAuthStrategy.java b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/EmailAuthStrategy.java
index a2636bc..38fdc44 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/EmailAuthStrategy.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/EmailAuthStrategy.java
@@ -23,6 +23,7 @@
import org.dromara.common.tenant.helper.TenantHelper;
import org.dromara.system.domain.SysClient;
import org.dromara.system.domain.SysUser;
+import org.dromara.system.domain.vo.SysClientVo;
import org.dromara.system.domain.vo.SysUserVo;
import org.dromara.system.mapper.SysUserMapper;
import org.dromara.web.domain.vo.LoginVo;
@@ -44,7 +45,7 @@
private final SysUserMapper userMapper;
@Override
- public LoginVo login(String body, SysClient client) {
+ public LoginVo login(String body, SysClientVo client) {
EmailLoginBody loginBody = JsonUtils.parseObject(body, EmailLoginBody.class);
ValidatorUtils.validate(loginBody);
String tenantId = loginBody.getTenantId();
@@ -90,9 +91,7 @@
private SysUserVo loadUserByEmail(String tenantId, String email) {
return TenantHelper.dynamic(tenantId, () -> {
- SysUser user = userMapper.selectOne(new LambdaQueryWrapper<SysUser>()
- .select(SysUser::getEmail, SysUser::getStatus)
- .eq(SysUser::getEmail, email));
+ SysUserVo user = userMapper.selectVoOne(new LambdaQueryWrapper<SysUser>().eq(SysUser::getEmail, email));
if (ObjectUtil.isNull(user)) {
log.info("鐧诲綍鐢ㄦ埛锛歿} 涓嶅瓨鍦�.", email);
throw new UserException("user.not.exists", email);
@@ -100,7 +99,7 @@
log.info("鐧诲綍鐢ㄦ埛锛歿} 宸茶鍋滅敤.", email);
throw new UserException("user.blocked", email);
}
- return userMapper.selectUserByEmail(email);
+ return user;
});
}
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/PasswordAuthStrategy.java b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/PasswordAuthStrategy.java
index bcb5916..cd33ea4 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/PasswordAuthStrategy.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/PasswordAuthStrategy.java
@@ -26,6 +26,7 @@
import org.dromara.common.web.config.properties.CaptchaProperties;
import org.dromara.system.domain.SysClient;
import org.dromara.system.domain.SysUser;
+import org.dromara.system.domain.vo.SysClientVo;
import org.dromara.system.domain.vo.SysUserVo;
import org.dromara.system.mapper.SysUserMapper;
import org.dromara.web.domain.vo.LoginVo;
@@ -48,7 +49,7 @@
private final SysUserMapper userMapper;
@Override
- public LoginVo login(String body, SysClient client) {
+ public LoginVo login(String body, SysClientVo client) {
PasswordLoginBody loginBody = JsonUtils.parseObject(body, PasswordLoginBody.class);
ValidatorUtils.validate(loginBody);
String tenantId = loginBody.getTenantId();
@@ -109,9 +110,7 @@
private SysUserVo loadUserByUsername(String tenantId, String username) {
return TenantHelper.dynamic(tenantId, () -> {
- SysUser user = userMapper.selectOne(new LambdaQueryWrapper<SysUser>()
- .select(SysUser::getUserName, SysUser::getStatus)
- .eq(SysUser::getUserName, username));
+ SysUserVo user = userMapper.selectVoOne(new LambdaQueryWrapper<SysUser>().eq(SysUser::getUserName, username));
if (ObjectUtil.isNull(user)) {
log.info("鐧诲綍鐢ㄦ埛锛歿} 涓嶅瓨鍦�.", username);
throw new UserException("user.not.exists", username);
@@ -119,7 +118,7 @@
log.info("鐧诲綍鐢ㄦ埛锛歿} 宸茶鍋滅敤.", username);
throw new UserException("user.blocked", username);
}
- return userMapper.selectUserByUserName(username);
+ return user;
});
}
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/SmsAuthStrategy.java b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/SmsAuthStrategy.java
index a4fa11c..f883632 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/SmsAuthStrategy.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/SmsAuthStrategy.java
@@ -23,6 +23,7 @@
import org.dromara.common.tenant.helper.TenantHelper;
import org.dromara.system.domain.SysClient;
import org.dromara.system.domain.SysUser;
+import org.dromara.system.domain.vo.SysClientVo;
import org.dromara.system.domain.vo.SysUserVo;
import org.dromara.system.mapper.SysUserMapper;
import org.dromara.web.domain.vo.LoginVo;
@@ -44,7 +45,7 @@
private final SysUserMapper userMapper;
@Override
- public LoginVo login(String body, SysClient client) {
+ public LoginVo login(String body, SysClientVo client) {
SmsLoginBody loginBody = JsonUtils.parseObject(body, SmsLoginBody.class);
ValidatorUtils.validate(loginBody);
String tenantId = loginBody.getTenantId();
@@ -90,9 +91,7 @@
private SysUserVo loadUserByPhonenumber(String tenantId, String phonenumber) {
return TenantHelper.dynamic(tenantId, () -> {
- SysUser user = userMapper.selectOne(new LambdaQueryWrapper<SysUser>()
- .select(SysUser::getPhonenumber, SysUser::getStatus)
- .eq(SysUser::getPhonenumber, phonenumber));
+ SysUserVo user = userMapper.selectVoOne(new LambdaQueryWrapper<SysUser>().eq(SysUser::getPhonenumber, phonenumber));
if (ObjectUtil.isNull(user)) {
log.info("鐧诲綍鐢ㄦ埛锛歿} 涓嶅瓨鍦�.", phonenumber);
throw new UserException("user.not.exists", phonenumber);
@@ -100,7 +99,7 @@
log.info("鐧诲綍鐢ㄦ埛锛歿} 宸茶鍋滅敤.", phonenumber);
throw new UserException("user.blocked", phonenumber);
}
- return userMapper.selectUserByPhonenumber(phonenumber);
+ return user;
});
}
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/SocialAuthStrategy.java b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/SocialAuthStrategy.java
index a12386e..6694165 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/SocialAuthStrategy.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/SocialAuthStrategy.java
@@ -7,7 +7,6 @@
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.http.HttpUtil;
import cn.hutool.http.Method;
-import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import me.zhyd.oauth.model.AuthResponse;
@@ -23,8 +22,7 @@
import org.dromara.common.social.config.properties.SocialProperties;
import org.dromara.common.social.utils.SocialUtils;
import org.dromara.common.tenant.helper.TenantHelper;
-import org.dromara.system.domain.SysClient;
-import org.dromara.system.domain.SysUser;
+import org.dromara.system.domain.vo.SysClientVo;
import org.dromara.system.domain.vo.SysSocialVo;
import org.dromara.system.domain.vo.SysUserVo;
import org.dromara.system.mapper.SysUserMapper;
@@ -59,7 +57,7 @@
* @param client 瀹㈡埛绔俊鎭�
*/
@Override
- public LoginVo login(String body, SysClient client) {
+ public LoginVo login(String body, SysClientVo client) {
SocialLoginBody loginBody = JsonUtils.parseObject(body, SocialLoginBody.class);
ValidatorUtils.validate(loginBody);
AuthResponse<AuthUser> response = SocialUtils.loginAuth(
@@ -83,11 +81,16 @@
if (CollUtil.isEmpty(list)) {
throw new ServiceException("浣犺繕娌℃湁缁戝畾绗笁鏂硅处鍙凤紝缁戝畾鍚庢墠鍙互鐧诲綍锛�");
}
- Optional<SysSocialVo> opt = list.stream().filter(x -> x.getTenantId().equals(loginBody.getTenantId())).findAny();
- if (opt.isEmpty()) {
- throw new ServiceException("瀵逛笉璧凤紝浣犳病鏈夋潈闄愮櫥褰曞綋鍓嶇鎴凤紒");
+ SysSocialVo social;
+ if (TenantHelper.isEnable()) {
+ Optional<SysSocialVo> opt = list.stream().filter(x -> x.getTenantId().equals(loginBody.getTenantId())).findAny();
+ if (opt.isEmpty()) {
+ throw new ServiceException("瀵逛笉璧凤紝浣犳病鏈夋潈闄愮櫥褰曞綋鍓嶇鎴凤紒");
+ }
+ social = opt.get();
+ } else {
+ social = list.get(0);
}
- SysSocialVo social = opt.get();
// 鏌ユ壘鐢ㄦ埛
SysUserVo user = loadUser(social.getTenantId(), social.getUserId());
@@ -114,9 +117,7 @@
private SysUserVo loadUser(String tenantId, Long userId) {
return TenantHelper.dynamic(tenantId, () -> {
- SysUser user = userMapper.selectOne(new LambdaQueryWrapper<SysUser>()
- .select(SysUser::getUserName, SysUser::getStatus)
- .eq(SysUser::getUserId, userId));
+ SysUserVo user = userMapper.selectVoById(userId);
if (ObjectUtil.isNull(user)) {
log.info("鐧诲綍鐢ㄦ埛锛歿} 涓嶅瓨鍦�.", "");
throw new UserException("user.not.exists", "");
@@ -124,7 +125,7 @@
log.info("鐧诲綍鐢ㄦ埛锛歿} 宸茶鍋滅敤.", "");
throw new UserException("user.blocked", "");
}
- return userMapper.selectUserByUserName(user.getUserName());
+ return user;
});
}
diff --git a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/XcxAuthStrategy.java b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/XcxAuthStrategy.java
index e5aef1f..aa8be73 100644
--- a/ruoyi-admin/src/main/java/org/dromara/web/service/impl/XcxAuthStrategy.java
+++ b/ruoyi-admin/src/main/java/org/dromara/web/service/impl/XcxAuthStrategy.java
@@ -12,6 +12,7 @@
import org.dromara.common.json.utils.JsonUtils;
import org.dromara.common.satoken.utils.LoginHelper;
import org.dromara.system.domain.SysClient;
+import org.dromara.system.domain.vo.SysClientVo;
import org.dromara.system.domain.vo.SysUserVo;
import org.dromara.web.domain.vo.LoginVo;
import org.dromara.web.service.IAuthStrategy;
@@ -19,7 +20,7 @@
import org.springframework.stereotype.Service;
/**
- * 閭欢璁よ瘉绛栫暐
+ * 灏忕▼搴忚璇佺瓥鐣�
*
* @author Michelle.Chung
*/
@@ -31,7 +32,7 @@
private final SysLoginService loginService;
@Override
- public LoginVo login(String body, SysClient client) {
+ public LoginVo login(String body, SysClientVo client) {
XcxLoginBody loginBody = JsonUtils.parseObject(body, XcxLoginBody.class);
ValidatorUtils.validate(loginBody);
// xcxCode 涓� 灏忕▼搴忚皟鐢� wx.login 鎺堟潈鍚庤幏鍙�
diff --git a/ruoyi-admin/src/main/resources/application-dev.yml b/ruoyi-admin/src/main/resources/application-dev.yml
index 4aaea57..529a106 100644
--- a/ruoyi-admin/src/main/resources/application-dev.yml
+++ b/ruoyi-admin/src/main/resources/application-dev.yml
@@ -8,21 +8,19 @@
username: ruoyi
password: 123456
---- # powerjob 閰嶇疆
-powerjob:
- worker:
- # 濡備綍寮�鍚皟搴︿腑蹇冭鏌ョ湅鏂囨。鏁欑▼
- enabled: false
- # 闇�瑕佸厛鍦� powerjob 鐧诲綍椤垫墽琛屽簲鐢ㄦ敞鍐屽悗鎵嶈兘浣跨敤
- app-name: ruoyi-worker
- allow-lazy-connect-server: false
- max-appended-wf-context-length: 4096
- max-result-length: 4096
- # 28080 绔彛 闅忕潃涓诲簲鐢ㄧ鍙i閫� 閬垮厤闆嗙兢鍐茬獊
- port: 2${server.port}
- protocol: http
- server-address: 127.0.0.1:7700
- store-strategy: disk
+--- # snail-job 閰嶇疆
+snail-job:
+ enabled: true
+ # 闇�瑕佸湪 SnailJob 鍚庡彴缁勭鐞嗗垱寤哄搴斿悕绉扮殑缁�,鐒跺悗鍒涘缓浠诲姟鐨勬椂鍊欓�夋嫨瀵瑰簲鐨勭粍,鎵嶈兘姝g‘鍒嗘淳浠诲姟
+ group-name: "ruoyi_group"
+ # SnailJob 鎺ュ叆楠岃瘉浠ょ墝 璇﹁ script/sql/snail_job.sql `sj_group_config` 琛�
+ token: "SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT"
+ server:
+ host: 127.0.0.1
+ port: 1788
+ # 璇﹁ script/sql/snail_job.sql `sj_namespace` 琛�
+ namespace: ${spring.profiles.active}
+
--- # 鏁版嵁婧愰厤缃�
spring:
@@ -43,7 +41,7 @@
driverClassName: com.mysql.cj.jdbc.Driver
# jdbc 鎵�鏈夊弬鏁伴厤缃弬鑰� https://lionli.blog.csdn.net/article/details/122018562
# rewriteBatchedStatements=true 鎵瑰鐞嗕紭鍖� 澶у箙鎻愬崌鎵归噺鎻掑叆鏇存柊鍒犻櫎鎬ц兘(瀵规暟鎹簱鏈夋�ц兘鎹熻�� 浣跨敤鎵归噺鎿嶄綔搴旇�冭檻鎬ц兘闂)
- url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true
+ url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true&nullCatalogMeansCurrent=true
username: root
password: root
# 浠庡簱鏁版嵁婧�
@@ -51,7 +49,7 @@
lazy: true
type: ${spring.datasource.type}
driverClassName: com.mysql.cj.jdbc.Driver
- url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true
+ url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true&nullCatalogMeansCurrent=true
username:
password:
# oracle:
@@ -149,36 +147,40 @@
connectionTimeout: 0
--- # sms 鐭俊 鏀寔 闃块噷浜� 鑵捐浜� 浜戠墖 绛夌瓑鍚勫紡鍚勬牱鐨勭煭淇℃湇鍔″晢
-# https://wind.kim/doc/start 鏂囨。鍦板潃 鍚勪釜鍘傚晢鍙悓鏃朵娇鐢�
+# https://sms4j.com/doc3/ 宸紓閰嶇疆鏂囨。鍦板潃 鏀寔鍗曞巶鍟嗗閰嶇疆锛屽彲浠ラ厤缃涓悓鏃朵娇鐢�
sms:
- # 闃块噷浜� dysmsapi.aliyuncs.com
- alibaba:
- #璇锋眰鍦板潃 榛樿涓� dysmsapi.aliyuncs.com 濡傛棤鐗规畩鏀瑰彉鍙互涓嶇敤璁剧疆
- requestUrl: dysmsapi.aliyuncs.com
- #闃块噷浜戠殑accessKey
- accessKeyId: xxxxxxx
- #闃块噷浜戠殑accessKeySecret
- accessKeySecret: xxxxxxx
- #鐭俊绛惧悕
- signature: 娴嬭瘯
- tencent:
- #璇锋眰鍦板潃榛樿涓� sms.tencentcloudapi.com 濡傛棤鐗规畩鏀瑰彉鍙笉鐢ㄨ缃�
- requestUrl: sms.tencentcloudapi.com
- #鑵捐浜戠殑accessKey
- accessKeyId: xxxxxxx
- #鑵捐浜戠殑accessKeySecret
- accessKeySecret: xxxxxxx
- #鐭俊绛惧悕
- signature: 娴嬭瘯
- #鐭俊sdkAppId
- sdkAppId: appid
- #鍦板煙淇℃伅榛樿涓� ap-guangzhou 濡傛棤鐗规畩鏀瑰彉鍙笉鐢ㄨ缃�
- territory: ap-guangzhou
+ # 閰嶇疆婧愮被鍨嬬敤浜庢爣瀹氶厤缃潵婧�(interface,yaml)
+ config-type: yaml
+ # 鐢ㄤ簬鏍囧畾yml涓殑閰嶇疆鏄惁寮�鍚煭淇℃嫤鎴紝鎺ュ彛閰嶇疆涓嶅彈姝ら檺鍒�
+ restricted: true
+ # 鐭俊鎷︽埅闄愬埗鍗曟墜鏈哄彿姣忓垎閽熸渶澶у彂閫侊紝鍙寮�鍚簡鎷︽埅鐨勯厤缃湁鏁�
+ minute-max: 1
+ # 鐭俊鎷︽埅闄愬埗鍗曟墜鏈哄彿姣忔棩鏈�澶у彂閫侀噺锛屽彧瀵瑰紑鍚簡鎷︽埅鐨勯厤缃湁鏁�
+ account-max: 30
+ # 浠ヤ笅閰嶇疆鏉ヨ嚜浜� org.dromara.sms4j.provider.config.BaseConfig绫讳腑
+ blends:
+ # 鍞竴ID 鐢ㄤ簬鍙戦�佺煭淇″鎵惧叿浣撻厤缃� 闅忎究瀹氫箟鍒敤涓枃鍗冲彲
+ # 鍙互鍚屾椂瀛樺湪涓や釜鐩稿悓鍘傚晢 渚嬪: ali1 ali2 涓や釜涓嶅悓鐨勯樋閲岀煭淇¤处鍙� 涔熷彲鐢ㄤ簬鍖哄垎绉熸埛
+ config1:
+ # 妗嗘灦瀹氫箟鐨勫巶鍟嗗悕绉版爣璇嗭紝鏍囧畾姝ら厤缃槸鍝釜鍘傚晢锛岃缁嗚鐪嬪巶鍟嗘爣璇嗕粙缁嶉儴鍒�
+ supplier: alibaba
+ # 鏈変簺绉颁负accessKey鏈変簺绉颁箣涓篴piKey锛屼篃鏈夌О涓簊dkKey鎴栬�卆ppId銆�
+ access-key-id: 鎮ㄧ殑accessKey
+ # 绉颁负accessSecret鏈変簺绉颁箣涓篴piSecret
+ access-key-secret: 鎮ㄧ殑accessKeySecret
+ signature: 鎮ㄧ殑鐭俊绛惧悕
+ sdk-app-id: 鎮ㄧ殑sdkAppId
+ config2:
+ # 鍘傚晢鏍囪瘑锛屾爣瀹氭閰嶇疆鏄摢涓巶鍟嗭紝璇︾粏璇风湅鍘傚晢鏍囪瘑浠嬬粛閮ㄥ垎
+ supplier: tencent
+ access-key-id: 鎮ㄧ殑accessKey
+ access-key-secret: 鎮ㄧ殑accessKeySecret
+ signature: 鎮ㄧ殑鐭俊绛惧悕
+ sdk-app-id: 鎮ㄧ殑sdkAppId
--- # 涓夋柟鎺堟潈
justauth:
- enabled: true
# 鍓嶇澶栫綉璁块棶鍦板潃
address: http://localhost:80
type:
@@ -189,6 +191,13 @@
client-id: 876892492581044224
client-secret: x1Y5MTMwNzIwMjMxNTM4NDc3Mzche8
redirect-uri: ${justauth.address}/social-callback?source=maxkey
+ topiam:
+ # topiam 鏈嶅姟鍣ㄥ湴鍧�
+ server-url: http://127.0.0.1:1989/api/v1/authorize/y0q************spq***********8ol
+ client-id: 449c4*********937************759
+ client-secret: ac7***********1e0************28d
+ redirect-uri: ${justauth.address}/social-callback?source=topiam
+ scopes: [openid, email, phone, profile]
qq:
client-id: 10**********6
client-secret: 1f7d08**********5b7**********29e
diff --git a/ruoyi-admin/src/main/resources/application-prod.yml b/ruoyi-admin/src/main/resources/application-prod.yml
index 782a680..0613bd7 100644
--- a/ruoyi-admin/src/main/resources/application-prod.yml
+++ b/ruoyi-admin/src/main/resources/application-prod.yml
@@ -11,21 +11,18 @@
username: ruoyi
password: 123456
---- # powerjob 閰嶇疆
-powerjob:
- worker:
- # 濡備綍寮�鍚皟搴︿腑蹇冭鏌ョ湅鏂囨。鏁欑▼
- enabled: false
- # 闇�瑕佸厛鍦� powerjob 鐧诲綍椤垫墽琛屽簲鐢ㄦ敞鍐屽悗鎵嶈兘浣跨敤
- app-name: ruoyi-worker
- allow-lazy-connect-server: false
- max-appended-wf-context-length: 4096
- max-result-length: 4096
- # 28080 绔彛 闅忕潃涓诲簲鐢ㄧ鍙i閫� 閬垮厤闆嗙兢鍐茬獊
- port: 2${server.port}
- protocol: http
- server-address: 127.0.0.1:7700
- store-strategy: disk
+--- # snail-job 閰嶇疆
+snail-job:
+ enabled: false
+ # 闇�瑕佸湪 SnailJob 鍚庡彴缁勭鐞嗗垱寤哄搴斿悕绉扮殑缁�,鐒跺悗鍒涘缓浠诲姟鐨勬椂鍊欓�夋嫨瀵瑰簲鐨勭粍,鎵嶈兘姝g‘鍒嗘淳浠诲姟
+ group-name: "ruoyi_group"
+ # SnailJob 鎺ュ叆楠岃瘉浠ょ墝 璇﹁ script/sql/snail_job.sql `sj_group_config` 琛�
+ token: "SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT"
+ server:
+ host: 127.0.0.1
+ port: 1788
+ # 璇﹁ script/sql/snail_job.sql `sj_namespace` 琛�
+ namespace: ${spring.profiles.active}
--- # 鏁版嵁婧愰厤缃�
spring:
@@ -46,7 +43,7 @@
driverClassName: com.mysql.cj.jdbc.Driver
# jdbc 鎵�鏈夊弬鏁伴厤缃弬鑰� https://lionli.blog.csdn.net/article/details/122018562
# rewriteBatchedStatements=true 鎵瑰鐞嗕紭鍖� 澶у箙鎻愬崌鎵归噺鎻掑叆鏇存柊鍒犻櫎鎬ц兘(瀵规暟鎹簱鏈夋�ц兘鎹熻�� 浣跨敤鎵归噺鎿嶄綔搴旇�冭檻鎬ц兘闂)
- url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true
+ url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true&nullCatalogMeansCurrent=true
username: root
password: root
# 浠庡簱鏁版嵁婧�
@@ -54,7 +51,7 @@
lazy: true
type: ${spring.datasource.type}
driverClassName: com.mysql.cj.jdbc.Driver
- url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true
+ url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true&nullCatalogMeansCurrent=true
username:
password:
# oracle:
@@ -152,35 +149,39 @@
connectionTimeout: 0
--- # sms 鐭俊 鏀寔 闃块噷浜� 鑵捐浜� 浜戠墖 绛夌瓑鍚勫紡鍚勬牱鐨勭煭淇℃湇鍔″晢
-# https://wind.kim/doc/start 鏂囨。鍦板潃 鍚勪釜鍘傚晢鍙悓鏃朵娇鐢�
+# https://sms4j.com/doc3/ 宸紓閰嶇疆鏂囨。鍦板潃 鏀寔鍗曞巶鍟嗗閰嶇疆锛屽彲浠ラ厤缃涓悓鏃朵娇鐢�
sms:
- # 闃块噷浜� dysmsapi.aliyuncs.com
- alibaba:
- #璇锋眰鍦板潃 榛樿涓� dysmsapi.aliyuncs.com 濡傛棤鐗规畩鏀瑰彉鍙互涓嶇敤璁剧疆
- requestUrl: dysmsapi.aliyuncs.com
- #闃块噷浜戠殑accessKey
- accessKeyId: xxxxxxx
- #闃块噷浜戠殑accessKeySecret
- accessKeySecret: xxxxxxx
- #鐭俊绛惧悕
- signature: 娴嬭瘯
- tencent:
- #璇锋眰鍦板潃榛樿涓� sms.tencentcloudapi.com 濡傛棤鐗规畩鏀瑰彉鍙笉鐢ㄨ缃�
- requestUrl: sms.tencentcloudapi.com
- #鑵捐浜戠殑accessKey
- accessKeyId: xxxxxxx
- #鑵捐浜戠殑accessKeySecret
- accessKeySecret: xxxxxxx
- #鐭俊绛惧悕
- signature: 娴嬭瘯
- #鐭俊sdkAppId
- sdkAppId: appid
- #鍦板煙淇℃伅榛樿涓� ap-guangzhou 濡傛棤鐗规畩鏀瑰彉鍙笉鐢ㄨ缃�
- territory: ap-guangzhou
+ # 閰嶇疆婧愮被鍨嬬敤浜庢爣瀹氶厤缃潵婧�(interface,yaml)
+ config-type: yaml
+ # 鐢ㄤ簬鏍囧畾yml涓殑閰嶇疆鏄惁寮�鍚煭淇℃嫤鎴紝鎺ュ彛閰嶇疆涓嶅彈姝ら檺鍒�
+ restricted: true
+ # 鐭俊鎷︽埅闄愬埗鍗曟墜鏈哄彿姣忓垎閽熸渶澶у彂閫侊紝鍙寮�鍚簡鎷︽埅鐨勯厤缃湁鏁�
+ minute-max: 1
+ # 鐭俊鎷︽埅闄愬埗鍗曟墜鏈哄彿姣忔棩鏈�澶у彂閫侀噺锛屽彧瀵瑰紑鍚簡鎷︽埅鐨勯厤缃湁鏁�
+ account-max: 30
+ # 浠ヤ笅閰嶇疆鏉ヨ嚜浜� org.dromara.sms4j.provider.config.BaseConfig绫讳腑
+ blends:
+ # 鍞竴ID 鐢ㄤ簬鍙戦�佺煭淇″鎵惧叿浣撻厤缃� 闅忎究瀹氫箟鍒敤涓枃鍗冲彲
+ # 鍙互鍚屾椂瀛樺湪涓や釜鐩稿悓鍘傚晢 渚嬪: ali1 ali2 涓や釜涓嶅悓鐨勯樋閲岀煭淇¤处鍙� 涔熷彲鐢ㄤ簬鍖哄垎绉熸埛
+ config1:
+ # 妗嗘灦瀹氫箟鐨勫巶鍟嗗悕绉版爣璇嗭紝鏍囧畾姝ら厤缃槸鍝釜鍘傚晢锛岃缁嗚鐪嬪巶鍟嗘爣璇嗕粙缁嶉儴鍒�
+ supplier: alibaba
+ # 鏈変簺绉颁负accessKey鏈変簺绉颁箣涓篴piKey锛屼篃鏈夌О涓簊dkKey鎴栬�卆ppId銆�
+ access-key-id: 鎮ㄧ殑accessKey
+ # 绉颁负accessSecret鏈変簺绉颁箣涓篴piSecret
+ access-key-secret: 鎮ㄧ殑accessKeySecret
+ signature: 鎮ㄧ殑鐭俊绛惧悕
+ sdk-app-id: 鎮ㄧ殑sdkAppId
+ config2:
+ # 鍘傚晢鏍囪瘑锛屾爣瀹氭閰嶇疆鏄摢涓巶鍟嗭紝璇︾粏璇风湅鍘傚晢鏍囪瘑浠嬬粛閮ㄥ垎
+ supplier: tencent
+ access-key-id: 鎮ㄧ殑accessKey
+ access-key-secret: 鎮ㄧ殑accessKeySecret
+ signature: 鎮ㄧ殑鐭俊绛惧悕
+ sdk-app-id: 鎮ㄧ殑sdkAppId
--- # 涓夋柟鎺堟潈
justauth:
- enabled: true
# 鍓嶇澶栫綉璁块棶鍦板潃
address: http://localhost:80
type:
@@ -191,6 +192,13 @@
client-id: 876892492581044224
client-secret: x1Y5MTMwNzIwMjMxNTM4NDc3Mzche8
redirect-uri: ${justauth.address}/social-callback?source=maxkey
+ topiam:
+ # topiam 鏈嶅姟鍣ㄥ湴鍧�
+ server-url: http://127.0.0.1:1989/api/v1/authorize/y0q************spq***********8ol
+ client-id: 449c4*********937************759
+ client-secret: ac7***********1e0************28d
+ redirect-uri: ${justauth.address}/social-callback?source=topiam
+ scopes: [ openid, email, phone, profile ]
qq:
client-id: 10**********6
client-secret: 1f7d08**********5b7**********29e
diff --git a/ruoyi-admin/src/main/resources/application.yml b/ruoyi-admin/src/main/resources/application.yml
index 3f54f64..27de286 100644
--- a/ruoyi-admin/src/main/resources/application.yml
+++ b/ruoyi-admin/src/main/resources/application.yml
@@ -5,7 +5,7 @@
# 鐗堟湰
version: ${revision}
# 鐗堟潈骞翠唤
- copyrightYear: 2023
+ copyrightYear: 2024
captcha:
enable: true
@@ -46,7 +46,7 @@
level:
org.dromara: @logging.level@
org.springframework: warn
- tech.powerjob.worker.background: warn
+ org.mybatis.spring.mapper: error
config: classpath:logback-plus.xml
# 鐢ㄦ埛閰嶇疆
@@ -61,6 +61,10 @@
spring:
application:
name: ${ruoyi.name}
+ threads:
+ # 寮�鍚櫄鎷熺嚎绋� 浠卝dk21鍙敤
+ virtual:
+ enabled: false
# 璧勬簮淇℃伅
messages:
# 鍥介檯鍖栬祫婧愭枃浠惰矾寰�
@@ -75,6 +79,8 @@
# 璁剧疆鎬讳笂浼犵殑鏂囦欢澶у皬
max-request-size: 20MB
mvc:
+ # 璁剧疆闈欐�佽祫婧愯矾寰� 闃叉鎵�鏈夎姹傞兘鍘绘煡闈欐�佽祫婧�
+ static-path-pattern: /static/**
format:
date-time: yyyy-MM-dd HH:mm:ss
jackson:
@@ -138,8 +144,7 @@
# MyBatisPlus閰嶇疆
# https://baomidou.com/config/
mybatis-plus:
- # 涓嶆敮鎸佸鍖�, 濡傛湁闇�瑕佸彲鍦ㄦ敞瑙i厤缃� 鎴� 鎻愬崌鎵寘绛夌骇
- # 渚嬪 com.**.**.mapper
+ # 澶氬寘鍚嶄娇鐢� 渚嬪 org.dromara.**.mapper,org.xxx.**.mapper
mapperPackage: org.dromara.**.mapper
# 瀵瑰簲鐨� XML 鏂囦欢浣嶇疆
mapperLocations: classpath*:mapper/**/*Mapper.xml
@@ -226,6 +231,7 @@
urlPatterns: /system/*,/monitor/*,/tool/*
# 鍏ㄥ眬绾跨▼姹犵浉鍏抽厤缃�
+# 濡備娇鐢↗DK21璇风洿鎺ヤ娇鐢ㄨ櫄鎷熺嚎绋� 涓嶈寮�鍚閰嶇疆
thread-pool:
# 鏄惁寮�鍚嚎绋嬫睜
enabled: false
@@ -261,3 +267,21 @@
path: /resource/websocket
# 璁剧疆璁块棶婧愬湴鍧�
allowedOrigins: '*'
+
+--- #flowable閰嶇疆
+flowable:
+ async-executor-activate: false #鍏抽棴瀹氭椂浠诲姟JOB
+ # 灏哾atabaseSchemaUpdate璁剧疆涓簍rue銆傚綋Flowable鍙戠幇搴撲笌鏁版嵁搴撹〃缁撴瀯涓嶄竴鑷存椂锛屼細鑷姩灏嗘暟鎹簱琛ㄧ粨鏋勫崌绾ц嚦鏂扮増鏈��
+ database-schema-update: true
+ activity-font-name: 瀹嬩綋
+ label-font-name: 瀹嬩綋
+ annotation-font-name: 瀹嬩綋
+ # 鍏抽棴鍚勪釜妯″潡鐢熸垚琛紝鐩墠鍙娇鐢ㄥ伐浣滄祦鍩虹琛�
+ idm:
+ enabled: false
+ cmmn:
+ enabled: false
+ dmn:
+ enabled: false
+ app:
+ enabled: false
diff --git a/ruoyi-admin/src/main/resources/ip2region.xdb b/ruoyi-admin/src/main/resources/ip2region.xdb
index 31f96a1..7052c05 100644
--- a/ruoyi-admin/src/main/resources/ip2region.xdb
+++ b/ruoyi-admin/src/main/resources/ip2region.xdb
Binary files differ
diff --git a/ruoyi-common/ruoyi-common-bom/pom.xml b/ruoyi-common/ruoyi-common-bom/pom.xml
index 004b035..f9af9de 100644
--- a/ruoyi-common/ruoyi-common-bom/pom.xml
+++ b/ruoyi-common/ruoyi-common-bom/pom.xml
@@ -14,7 +14,7 @@
</description>
<properties>
- <revision>5.1.2</revision>
+ <revision>5.2.0-BETA</revision>
</properties>
<dependencyManagement>
diff --git a/ruoyi-common/ruoyi-common-core/pom.xml b/ruoyi-common/ruoyi-common-core/pom.xml
index ad37e90..5925c9b 100644
--- a/ruoyi-common/ruoyi-common-core/pom.xml
+++ b/ruoyi-common/ruoyi-common-core/pom.xml
@@ -94,6 +94,11 @@
<artifactId>ip2region</artifactId>
</dependency>
+ <dependency>
+ <groupId>com.alibaba</groupId>
+ <artifactId>transmittable-thread-local</artifactId>
+ </dependency>
+
</dependencies>
</project>
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/ApplicationConfig.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/ApplicationConfig.java
index 07500ba..d120087 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/ApplicationConfig.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/ApplicationConfig.java
@@ -2,6 +2,7 @@
import org.springframework.boot.autoconfigure.AutoConfiguration;
import org.springframework.context.annotation.EnableAspectJAutoProxy;
+import org.springframework.scheduling.annotation.EnableAsync;
/**
* 绋嬪簭娉ㄨВ閰嶇疆
@@ -11,6 +12,7 @@
@AutoConfiguration
// 琛ㄧず閫氳繃aop妗嗘灦鏆撮湶璇ヤ唬鐞嗗璞�,AopContext鑳藉璁块棶
@EnableAspectJAutoProxy(exposeProxy = true)
+@EnableAsync(proxyTargetClass = true)
public class ApplicationConfig {
}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/AsyncConfig.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/AsyncConfig.java
index 9a32afe..cd01e33 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/AsyncConfig.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/config/AsyncConfig.java
@@ -5,18 +5,19 @@
import org.dromara.common.core.utils.SpringUtils;
import org.springframework.aop.interceptor.AsyncUncaughtExceptionHandler;
import org.springframework.boot.autoconfigure.AutoConfiguration;
+import org.springframework.core.task.VirtualThreadTaskExecutor;
import org.springframework.scheduling.annotation.AsyncConfigurer;
-import org.springframework.scheduling.annotation.EnableAsync;
import java.util.Arrays;
import java.util.concurrent.Executor;
/**
* 寮傛閰嶇疆
+ * <p>
+ * 濡傛灉鏈娇鐢ㄨ櫄鎷熺嚎绋嬪垯鐢熸晥
*
* @author Lion Li
*/
-@EnableAsync(proxyTargetClass = true)
@AutoConfiguration
public class AsyncConfig implements AsyncConfigurer {
@@ -25,6 +26,9 @@
*/
@Override
public Executor getAsyncExecutor() {
+ if(SpringUtils.isVirtual()) {
+ return new VirtualThreadTaskExecutor("async-");
+ }
return SpringUtils.getBean("scheduledExecutorService");
}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/constant/CacheNames.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/constant/CacheNames.java
index e59277a..28ba177 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/constant/CacheNames.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/constant/CacheNames.java
@@ -36,6 +36,11 @@
String SYS_TENANT = GlobalConstants.GLOBAL_REDIS_KEY + "sys_tenant#30d";
/**
+ * 瀹㈡埛绔�
+ */
+ String SYS_CLIENT = GlobalConstants.GLOBAL_REDIS_KEY + "sys_client#30d";
+
+ /**
* 鐢ㄦ埛璐︽埛
*/
String SYS_USER_NAME = "sys_user_name#30d";
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/constant/RegexConstants.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/constant/RegexConstants.java
new file mode 100644
index 0000000..77eed8c
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/constant/RegexConstants.java
@@ -0,0 +1,54 @@
+package org.dromara.common.core.constant;
+
+import cn.hutool.core.lang.RegexPool;
+
+/**
+ * 甯哥敤姝e垯琛ㄨ揪寮忓瓧绗︿覆
+ * <p>
+ * 甯哥敤姝e垯琛ㄨ揪寮忛泦鍚堬紝鏇村姝e垯瑙�: https://any86.github.io/any-rule/
+ *
+ * @author Feng
+ */
+public interface RegexConstants extends RegexPool {
+
+ /**
+ * 瀛楀吀绫诲瀷蹇呴』浠ュ瓧姣嶅紑澶达紝涓斿彧鑳戒负锛堝皬鍐欏瓧姣嶏紝鏁板瓧锛屼笅婊戠嚎锛�
+ */
+ String DICTIONARY_TYPE = "^[a-z][a-z0-9_]*$";
+
+ /**
+ * 鏉冮檺鏍囪瘑蹇呴』绗﹀悎 tool:build:list 鏍煎紡锛屾垨鑰呯┖瀛楃涓�
+ */
+ String PERMISSION_STRING = "^(|^[a-zA-Z0-9_]+:[a-zA-Z0-9_]+:[a-zA-Z0-9_]+)$";
+
+ /**
+ * 韬唤璇佸彿鐮侊紙鍚�6浣嶏級
+ */
+ String ID_CARD_LAST_6 = "^(([0-2][1-9])|10|20|30|31)\\d{3}[0-9Xx]$";
+
+ /**
+ * QQ鍙风爜
+ */
+ String QQ_NUMBER = "^[1-9][0-9]\\d{4,9}$";
+
+ /**
+ * 閭斂缂栫爜
+ */
+ String POSTAL_CODE = "^[1-9]\\d{5}$";
+
+ /**
+ * 娉ㄥ唽璐﹀彿
+ */
+ String ACCOUNT = "^[a-zA-Z][a-zA-Z0-9_]{4,15}$";
+
+ /**
+ * 瀵嗙爜锛氬寘鍚嚦灏�8涓瓧绗︼紝鍖呮嫭澶у啓瀛楁瘝銆佸皬鍐欏瓧姣嶃�佹暟瀛楀拰鐗规畩瀛楃
+ */
+ String PASSWORD = "^(?=.*[a-z])(?=.*[A-Z])(?=.*\\d)(?=.*[@$!%*?&])[A-Za-z\\d@$!%*?&]{8,}$";
+
+ /**
+ * 閫氱敤鐘舵�侊紙0琛ㄧず姝e父锛�1琛ㄧず鍋滅敤锛�
+ */
+ String STATUS = "^[01]$";
+
+}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/OssDTO.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/OssDTO.java
new file mode 100644
index 0000000..463821c
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/OssDTO.java
@@ -0,0 +1,46 @@
+package org.dromara.common.core.domain.dto;
+
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * OSS瀵硅薄
+ *
+ * @author Lion Li
+ */
+@Data
+@NoArgsConstructor
+public class OssDTO implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 瀵硅薄瀛樺偍涓婚敭
+ */
+ private Long ossId;
+
+ /**
+ * 鏂囦欢鍚�
+ */
+ private String fileName;
+
+ /**
+ * 鍘熷悕
+ */
+ private String originalName;
+
+ /**
+ * 鏂囦欢鍚庣紑鍚�
+ */
+ private String fileSuffix;
+
+ /**
+ * URL鍦板潃
+ */
+ private String url;
+
+}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/RoleDTO.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/RoleDTO.java
index 03d6166..aea8e7a 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/RoleDTO.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/RoleDTO.java
@@ -3,6 +3,7 @@
import lombok.Data;
import lombok.NoArgsConstructor;
+import java.io.Serial;
import java.io.Serializable;
/**
@@ -15,6 +16,9 @@
@NoArgsConstructor
public class RoleDTO implements Serializable {
+ @Serial
+ private static final long serialVersionUID = 1L;
+
/**
* 瑙掕壊ID
*/
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/UserDTO.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/UserDTO.java
new file mode 100644
index 0000000..cb5def9
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/dto/UserDTO.java
@@ -0,0 +1,73 @@
+package org.dromara.common.core.domain.dto;
+
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.Date;
+
+
+/**
+ * 鐢ㄦ埛
+ *
+ * @author Michelle.Chung
+ */
+@Data
+@NoArgsConstructor
+public class UserDTO implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 鐢ㄦ埛ID
+ */
+ private Long userId;
+
+ /**
+ * 閮ㄩ棬ID
+ */
+ private Long deptId;
+
+ /**
+ * 鐢ㄦ埛璐﹀彿
+ */
+ private String userName;
+
+ /**
+ * 鐢ㄦ埛鏄电О
+ */
+ private String nickName;
+
+ /**
+ * 鐢ㄦ埛绫诲瀷锛坰ys_user绯荤粺鐢ㄦ埛锛�
+ */
+ private String userType;
+
+ /**
+ * 鐢ㄦ埛閭
+ */
+ private String email;
+
+ /**
+ * 鎵嬫満鍙风爜
+ */
+ private String phonenumber;
+
+ /**
+ * 鐢ㄦ埛鎬у埆锛�0鐢� 1濂� 2鏈煡锛�
+ */
+ private String sex;
+
+ /**
+ * 甯愬彿鐘舵�侊紙0姝e父 1鍋滅敤锛�
+ */
+ private String status;
+
+ /**
+ * 鍒涘缓鏃堕棿
+ */
+ private Date createTime;
+
+}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/model/LoginUser.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/model/LoginUser.java
index e267124..c723e76 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/model/LoginUser.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/domain/model/LoginUser.java
@@ -14,7 +14,6 @@
*
* @author Lion Li
*/
-
@Data
@NoArgsConstructor
public class LoginUser implements Serializable {
@@ -38,6 +37,11 @@
private Long deptId;
/**
+ * 閮ㄩ棬绫诲埆缂栫爜
+ */
+ private String deptCategory;
+
+ /**
* 閮ㄩ棬鍚�
*/
private String deptName;
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/exception/ServiceException.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/exception/ServiceException.java
index 4fb097a..e9dc6ec 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/exception/ServiceException.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/exception/ServiceException.java
@@ -1,9 +1,6 @@
package org.dromara.common.core.exception;
-import lombok.AllArgsConstructor;
-import lombok.Data;
-import lombok.EqualsAndHashCode;
-import lombok.NoArgsConstructor;
+import lombok.*;
import java.io.Serial;
@@ -45,17 +42,9 @@
this.code = code;
}
- public String getDetailMessage() {
- return detailMessage;
- }
-
@Override
public String getMessage() {
return message;
- }
-
- public Integer getCode() {
- return code;
}
public ServiceException setMessage(String message) {
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/factory/RegexPatternPoolFactory.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/factory/RegexPatternPoolFactory.java
new file mode 100644
index 0000000..fd907d2
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/factory/RegexPatternPoolFactory.java
@@ -0,0 +1,52 @@
+package org.dromara.common.core.factory;
+
+import cn.hutool.core.lang.PatternPool;
+import org.dromara.common.core.constant.RegexConstants;
+
+import java.util.regex.Pattern;
+
+/**
+ * 姝e垯琛ㄨ揪寮忔ā寮忔睜宸ュ巶
+ * <p>鍒濆鍖栫殑鏃跺�欏皢姝e垯琛ㄨ揪寮忓姞鍏ョ紦瀛樻睜褰撲腑</p>
+ * <p>鎻愰珮姝e垯琛ㄨ揪寮忕殑鎬ц兘锛岄伩鍏嶉噸澶嶇紪璇戠浉鍚岀殑姝e垯琛ㄨ揪寮�</p>
+ *
+ * @author 21001
+ */
+public class RegexPatternPoolFactory extends PatternPool {
+
+ /**
+ * 瀛楀吀绫诲瀷蹇呴』浠ュ瓧姣嶅紑澶达紝涓斿彧鑳戒负锛堝皬鍐欏瓧姣嶏紝鏁板瓧锛屼笅婊戠嚎锛�
+ */
+ public static final Pattern DICTIONARY_TYPE = get(RegexConstants.DICTIONARY_TYPE);
+
+ /**
+ * 韬唤璇佸彿鐮侊紙鍚�6浣嶏級
+ */
+ public static final Pattern ID_CARD_LAST_6 = get(RegexConstants.ID_CARD_LAST_6);
+
+ /**
+ * QQ鍙风爜
+ */
+ public static final Pattern QQ_NUMBER = get(RegexConstants.QQ_NUMBER);
+
+ /**
+ * 閭斂缂栫爜
+ */
+ public static final Pattern POSTAL_CODE = get(RegexConstants.POSTAL_CODE);
+
+ /**
+ * 娉ㄥ唽璐﹀彿
+ */
+ public static final Pattern ACCOUNT = get(RegexConstants.ACCOUNT);
+
+ /**
+ * 瀵嗙爜锛氬寘鍚嚦灏�8涓瓧绗︼紝鍖呮嫭澶у啓瀛楁瘝銆佸皬鍐欏瓧姣嶃�佹暟瀛楀拰鐗规畩瀛楃
+ */
+ public static final Pattern PASSWORD = get(RegexConstants.PASSWORD);
+
+ /**
+ * 閫氱敤鐘舵�侊紙0琛ㄧず姝e父锛�1琛ㄧず鍋滅敤锛�
+ */
+ public static final Pattern STATUS = get(RegexConstants.STATUS);
+
+}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/OssService.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/OssService.java
index 43742b3..1a52de0 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/OssService.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/OssService.java
@@ -1,5 +1,9 @@
package org.dromara.common.core.service;
+import org.dromara.common.core.domain.dto.OssDTO;
+
+import java.util.List;
+
/**
* 閫氱敤 OSS鏈嶅姟
*
@@ -15,4 +19,11 @@
*/
String selectUrlByIds(String ossIds);
+ /**
+ * 閫氳繃ossId鏌ヨ鍒楄〃
+ *
+ * @param ossIds ossId涓查�楀彿鍒嗛殧
+ * @return 鍒楄〃
+ */
+ List<OssDTO> selectByIds(String ossIds);
}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/UserService.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/UserService.java
index d6b312a..0f2878d 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/UserService.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/service/UserService.java
@@ -1,5 +1,9 @@
package org.dromara.common.core.service;
+import org.dromara.common.core.domain.dto.UserDTO;
+
+import java.util.List;
+
/**
* 閫氱敤 鐢ㄦ埛鏈嶅姟
*
@@ -19,8 +23,47 @@
* 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛璐︽埛
*
* @param userId 鐢ㄦ埛ID
- * @return 鐢ㄦ埛璐︽埛
+ * @return 鐢ㄦ埛鍚嶇О
*/
String selectNicknameById(Long userId);
+ /**
+ * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛璐︽埛
+ *
+ * @param userIds 鐢ㄦ埛ID 澶氫釜鐢ㄩ�楀彿闅斿紑
+ * @return 鐢ㄦ埛鍚嶇О
+ */
+ String selectNicknameByIds(String userIds);
+
+ /**
+ * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛鎵嬫満鍙�
+ *
+ * @param userId 鐢ㄦ埛id
+ * @return 鐢ㄦ埛鎵嬫満鍙�
+ */
+ String selectPhonenumberById(Long userId);
+
+ /**
+ * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛閭
+ *
+ * @param userId 鐢ㄦ埛id
+ * @return 鐢ㄦ埛閭
+ */
+ String selectEmailById(Long userId);
+
+ /**
+ * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛鍒楄〃
+ *
+ * @param userIds 鐢ㄦ埛ids
+ * @return 鐢ㄦ埛鍒楄〃
+ */
+ List<UserDTO> selectListByIds(List<Long> userIds);
+
+ /**
+ * 閫氳繃瑙掕壊ID鏌ヨ鐢ㄦ埛ID
+ *
+ * @param roleIds 瑙掕壊ids
+ * @return 鐢ㄦ埛ids
+ */
+ List<Long> selectUserIdsByRoleIds(List<Long> roleIds);
}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/SpringUtils.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/SpringUtils.java
index ab50539..e58c394 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/SpringUtils.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/SpringUtils.java
@@ -3,7 +3,9 @@
import cn.hutool.extra.spring.SpringUtil;
import org.springframework.aop.framework.AopContext;
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
+import org.springframework.boot.autoconfigure.thread.Threading;
import org.springframework.context.ApplicationContext;
+import org.springframework.core.env.Environment;
import org.springframework.stereotype.Component;
/**
@@ -59,4 +61,8 @@
return getApplicationContext();
}
+ public static boolean isVirtual() {
+ return Threading.VIRTUAL.isActive(getBean(Environment.class));
+ }
+
}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/StringUtils.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/StringUtils.java
index 5e4db50..dd6ebb1 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/StringUtils.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/StringUtils.java
@@ -22,6 +22,8 @@
public static final String SEPARATOR = ",";
+ public static final String SLASH = "/";
+
/**
* 鑾峰彇鍙傛暟涓嶄负绌哄��
*
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/ValidatorUtils.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/ValidatorUtils.java
index f94f916..06b8fd6 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/ValidatorUtils.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/ValidatorUtils.java
@@ -1,11 +1,11 @@
package org.dromara.common.core.utils;
-import lombok.AccessLevel;
-import lombok.NoArgsConstructor;
-
import jakarta.validation.ConstraintViolation;
import jakarta.validation.ConstraintViolationException;
import jakarta.validation.Validator;
+import lombok.AccessLevel;
+import lombok.NoArgsConstructor;
+
import java.util.Set;
/**
@@ -18,6 +18,13 @@
private static final Validator VALID = SpringUtils.getBean(Validator.class);
+ /**
+ * 瀵圭粰瀹氬璞¤繘琛屽弬鏁版牎楠岋紝骞舵牴鎹寚瀹氱殑鏍¢獙缁勮繘琛屾牎楠�
+ *
+ * @param object 瑕佽繘琛屾牎楠岀殑瀵硅薄
+ * @param groups 鏍¢獙缁�
+ * @throws ConstraintViolationException 濡傛灉鏍¢獙涓嶉�氳繃锛屽垯鎶涘嚭鍙傛暟鏍¢獙寮傚父
+ */
public static <T> void validate(T object, Class<?>... groups) {
Set<ConstraintViolation<T>> validate = VALID.validate(object, groups);
if (!validate.isEmpty()) {
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/regex/RegexUtils.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/regex/RegexUtils.java
new file mode 100644
index 0000000..b8b12d4
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/regex/RegexUtils.java
@@ -0,0 +1,30 @@
+package org.dromara.common.core.utils.regex;
+
+
+import cn.hutool.core.util.ReUtil;
+import org.dromara.common.core.constant.RegexConstants;
+
+/**
+ * 姝e垯鐩稿叧宸ュ叿绫�
+ *
+ * @author Feng
+ */
+public final class RegexUtils extends ReUtil {
+
+ /**
+ * 浠庤緭鍏ュ瓧绗︿覆涓彁鍙栧尮閰嶇殑閮ㄥ垎锛屽鏋滄病鏈夊尮閰嶅垯杩斿洖榛樿鍊�
+ *
+ * @param input 瑕佹彁鍙栫殑杈撳叆瀛楃涓�
+ * @param regex 鐢ㄤ簬鍖归厤鐨勬鍒欒〃杈惧紡锛屽彲浠ヤ娇鐢� {@link RegexConstants} 涓畾涔夌殑甯搁噺
+ * @param defaultInput 濡傛灉娌℃湁鍖归厤鏃惰繑鍥炵殑榛樿鍊�
+ * @return 濡傛灉鎵惧埌鍖归厤鐨勯儴鍒嗭紝鍒欒繑鍥炲尮閰嶇殑閮ㄥ垎锛屽惁鍒欒繑鍥為粯璁ゅ��
+ */
+ public static String extractFromString(String input, String regex, String defaultInput) {
+ try {
+ return ReUtil.get(regex, input, 1);
+ } catch (Exception e) {
+ return defaultInput;
+ }
+ }
+
+}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/regex/RegexValidator.java b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/regex/RegexValidator.java
new file mode 100644
index 0000000..c0dda20
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/org/dromara/common/core/utils/regex/RegexValidator.java
@@ -0,0 +1,105 @@
+package org.dromara.common.core.utils.regex;
+
+import cn.hutool.core.exceptions.ValidateException;
+import cn.hutool.core.lang.Validator;
+import org.dromara.common.core.factory.RegexPatternPoolFactory;
+
+import java.util.regex.Pattern;
+
+/**
+ * 姝e垯瀛楁鏍¢獙鍣�
+ * 涓昏楠岃瘉瀛楁闈炵┖銆佹槸鍚︿负婊¤冻鎸囧畾鏍煎紡绛�
+ *
+ * @author Feng
+ */
+public class RegexValidator extends Validator {
+
+ /**
+ * 瀛楀吀绫诲瀷蹇呴』浠ュ瓧姣嶅紑澶达紝涓斿彧鑳戒负锛堝皬鍐欏瓧姣嶏紝鏁板瓧锛屼笅婊戠嚎锛�
+ */
+ public static final Pattern DICTIONARY_TYPE = RegexPatternPoolFactory.DICTIONARY_TYPE;
+
+ /**
+ * 韬唤璇佸彿鐮侊紙鍚�6浣嶏級
+ */
+ public static final Pattern ID_CARD_LAST_6 = RegexPatternPoolFactory.ID_CARD_LAST_6;
+
+ /**
+ * QQ鍙风爜
+ */
+ public static final Pattern QQ_NUMBER = RegexPatternPoolFactory.QQ_NUMBER;
+
+ /**
+ * 閭斂缂栫爜
+ */
+ public static final Pattern POSTAL_CODE = RegexPatternPoolFactory.POSTAL_CODE;
+
+ /**
+ * 娉ㄥ唽璐﹀彿
+ */
+ public static final Pattern ACCOUNT = RegexPatternPoolFactory.ACCOUNT;
+
+ /**
+ * 瀵嗙爜锛氬寘鍚嚦灏�8涓瓧绗︼紝鍖呮嫭澶у啓瀛楁瘝銆佸皬鍐欏瓧姣嶃�佹暟瀛楀拰鐗规畩瀛楃
+ */
+ public static final Pattern PASSWORD = RegexPatternPoolFactory.PASSWORD;
+
+ /**
+ * 閫氱敤鐘舵�侊紙0琛ㄧず姝e父锛�1琛ㄧず鍋滅敤锛�
+ */
+ public static final Pattern STATUS = RegexPatternPoolFactory.STATUS;
+
+
+ /**
+ * 妫�鏌ヨ緭鍏ョ殑璐﹀彿鏄惁鍖归厤棰勫畾涔夌殑瑙勫垯
+ *
+ * @param value 瑕侀獙璇佺殑璐﹀彿
+ * @return 濡傛灉璐﹀彿绗﹀悎瑙勫垯锛岃繑鍥� true锛涘惁鍒欙紝杩斿洖 false銆�
+ */
+ public static boolean isAccount(CharSequence value) {
+ return isMatchRegex(ACCOUNT, value);
+ }
+
+ /**
+ * 楠岃瘉杈撳叆鐨勮处鍙锋槸鍚︾鍚堣鍒欙紝濡傛灉涓嶇鍚堬紝鍒欐姏鍑� ValidateException 寮傚父
+ *
+ * @param value 瑕侀獙璇佺殑璐﹀彿
+ * @param errorMsg 楠岃瘉澶辫触鏃舵姏鍑虹殑寮傚父娑堟伅
+ * @param <T> CharSequence 鐨勫瓙绫诲瀷
+ * @return 濡傛灉楠岃瘉閫氳繃锛岃繑鍥炶緭鍏ョ殑璐﹀彿
+ * @throws ValidateException 濡傛灉楠岃瘉澶辫触
+ */
+ public static <T extends CharSequence> T validateAccount(T value, String errorMsg) throws ValidateException {
+ if (!isAccount(value)) {
+ throw new ValidateException(errorMsg);
+ }
+ return value;
+ }
+
+ /**
+ * 妫�鏌ヨ緭鍏ョ殑鐘舵�佹槸鍚﹀尮閰嶉瀹氫箟鐨勮鍒�
+ *
+ * @param value 瑕侀獙璇佺殑鐘舵��
+ * @return 濡傛灉鐘舵�佺鍚堣鍒欙紝杩斿洖 true锛涘惁鍒欙紝杩斿洖 false銆�
+ */
+ public static boolean isStatus(CharSequence value) {
+ return isMatchRegex(STATUS, value);
+ }
+
+ /**
+ * 楠岃瘉杈撳叆鐨勭姸鎬佹槸鍚︾鍚堣鍒欙紝濡傛灉涓嶇鍚堬紝鍒欐姏鍑� ValidateException 寮傚父
+ *
+ * @param value 瑕侀獙璇佺殑鐘舵��
+ * @param errorMsg 楠岃瘉澶辫触鏃舵姏鍑虹殑寮傚父娑堟伅
+ * @param <T> CharSequence 鐨勫瓙绫诲瀷
+ * @return 濡傛灉楠岃瘉閫氳繃锛岃繑鍥炶緭鍏ョ殑鐘舵��
+ * @throws ValidateException 濡傛灉楠岃瘉澶辫触
+ */
+ public static <T extends CharSequence> T validateStatus(T value, String errorMsg) throws ValidateException {
+ if (!isStatus(value)) {
+ throw new ValidateException(errorMsg);
+ }
+ return value;
+ }
+
+}
diff --git a/ruoyi-common/ruoyi-common-encrypt/pom.xml b/ruoyi-common/ruoyi-common-encrypt/pom.xml
index df3222b..ed4910e 100644
--- a/ruoyi-common/ruoyi-common-encrypt/pom.xml
+++ b/ruoyi-common/ruoyi-common-encrypt/pom.xml
@@ -23,11 +23,6 @@
</dependency>
<dependency>
- <groupId>org.mybatis.spring.boot</groupId>
- <artifactId>mybatis-spring-boot-starter</artifactId>
- </dependency>
-
- <dependency>
<groupId>org.bouncycastle</groupId>
<artifactId>bcprov-jdk15to18</artifactId>
</dependency>
@@ -42,6 +37,18 @@
<artifactId>spring-webmvc</artifactId>
</dependency>
+ <dependency>
+ <groupId>com.baomidou</groupId>
+ <artifactId>mybatis-plus-spring-boot3-starter</artifactId>
+ <optional>true</optional>
+ <exclusions>
+ <exclusion>
+ <groupId>org.mybatis</groupId>
+ <artifactId>mybatis-spring</artifactId>
+ </exclusion>
+ </exclusions>
+ </dependency>
+
</dependencies>
</project>
diff --git a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/config/EncryptorAutoConfiguration.java b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/config/EncryptorAutoConfiguration.java
index e988a3a..fbc4e52 100644
--- a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/config/EncryptorAutoConfiguration.java
+++ b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/config/EncryptorAutoConfiguration.java
@@ -1,5 +1,8 @@
package org.dromara.common.encrypt.config;
+import com.baomidou.mybatisplus.autoconfigure.MybatisPlusAutoConfiguration;
+import com.baomidou.mybatisplus.autoconfigure.MybatisPlusProperties;
+import lombok.extern.slf4j.Slf4j;
import org.dromara.common.encrypt.core.EncryptorManager;
import org.dromara.common.encrypt.interceptor.MybatisDecryptInterceptor;
import org.dromara.common.encrypt.interceptor.MybatisEncryptInterceptor;
@@ -16,17 +19,18 @@
* @author 鑰侀┈
* @version 4.6.0
*/
-@AutoConfiguration
+@AutoConfiguration(after = MybatisPlusAutoConfiguration.class)
@EnableConfigurationProperties(EncryptorProperties.class)
@ConditionalOnProperty(value = "mybatis-encryptor.enable", havingValue = "true")
+@Slf4j
public class EncryptorAutoConfiguration {
@Autowired
private EncryptorProperties properties;
@Bean
- public EncryptorManager encryptorManager() {
- return new EncryptorManager();
+ public EncryptorManager encryptorManager(MybatisPlusProperties mybatisPlusProperties) {
+ return new EncryptorManager(mybatisPlusProperties.getTypeAliasesPackage());
}
@Bean
@@ -38,4 +42,8 @@
public MybatisDecryptInterceptor mybatisDecryptInterceptor(EncryptorManager encryptorManager) {
return new MybatisDecryptInterceptor(encryptorManager, properties);
}
+
}
+
+
+
diff --git a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/core/EncryptorManager.java b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/core/EncryptorManager.java
index 498b4b8..a6d3cf9 100644
--- a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/core/EncryptorManager.java
+++ b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/core/EncryptorManager.java
@@ -1,14 +1,23 @@
package org.dromara.common.encrypt.core;
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.ReflectUtil;
+import lombok.NoArgsConstructor;
import lombok.extern.slf4j.Slf4j;
+import org.apache.ibatis.io.Resources;
+import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.encrypt.annotation.EncryptField;
+import org.springframework.context.ConfigurableApplicationContext;
+import org.springframework.core.io.Resource;
+import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
+import org.springframework.core.io.support.ResourcePatternResolver;
+import org.springframework.core.type.ClassMetadata;
+import org.springframework.core.type.classreading.CachingMetadataReaderFactory;
+import org.springframework.util.ClassUtils;
import java.lang.reflect.Field;
-import java.util.Arrays;
-import java.util.HashSet;
-import java.util.Map;
-import java.util.Set;
+import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import java.util.stream.Collectors;
@@ -19,6 +28,7 @@
* @version 4.6.0
*/
@Slf4j
+@NoArgsConstructor
public class EncryptorManager {
/**
@@ -32,24 +42,23 @@
Map<Class<?>, Set<Field>> fieldCache = new ConcurrentHashMap<>();
/**
+ * 鏋勯�犳柟娉曚紶鍏ョ被鍔犲瘑瀛楁缂撳瓨
+ *
+ * @param typeAliasesPackage 瀹炰綋绫诲寘
+ */
+ public EncryptorManager(String typeAliasesPackage) {
+ scanEncryptClasses(typeAliasesPackage);
+ }
+
+
+ /**
* 鑾峰彇绫诲姞瀵嗗瓧娈电紦瀛�
*/
public Set<Field> getFieldCache(Class<?> sourceClazz) {
- return fieldCache.computeIfAbsent(sourceClazz, clazz -> {
- Set<Field> fieldSet = new HashSet<>();
- while (clazz != null) {
- Field[] fields = clazz.getDeclaredFields();
- fieldSet.addAll(Arrays.asList(fields));
- clazz = clazz.getSuperclass();
- }
- fieldSet = fieldSet.stream().filter(field ->
- field.isAnnotationPresent(EncryptField.class) && field.getType() == String.class)
- .collect(Collectors.toSet());
- for (Field field : fieldSet) {
- field.setAccessible(true);
- }
- return fieldSet;
- });
+ if (ObjectUtil.isNotNull(fieldCache)) {
+ return fieldCache.get(sourceClazz);
+ }
+ return null;
}
/**
@@ -97,4 +106,53 @@
return encryptor.decrypt(value);
}
+ /**
+ * 閫氳繃 typeAliasesPackage 璁剧疆鐨勬壂鎻忓寘 鎵弿缂撳瓨瀹炰綋
+ */
+ private void scanEncryptClasses(String typeAliasesPackage) {
+ PathMatchingResourcePatternResolver resolver = new PathMatchingResourcePatternResolver();
+ CachingMetadataReaderFactory factory = new CachingMetadataReaderFactory();
+ String[] packagePatternArray = StringUtils.splitPreserveAllTokens(typeAliasesPackage, ConfigurableApplicationContext.CONFIG_LOCATION_DELIMITERS);
+ String classpath = ResourcePatternResolver.CLASSPATH_ALL_URL_PREFIX;
+ try {
+ for (String packagePattern : packagePatternArray) {
+ String path = ClassUtils.convertClassNameToResourcePath(packagePattern);
+ Resource[] resources = resolver.getResources(classpath + path + "/*.class");
+ for (Resource resource : resources) {
+ ClassMetadata classMetadata = factory.getMetadataReader(resource).getClassMetadata();
+ Class<?> clazz = Resources.classForName(classMetadata.getClassName());
+ Set<Field> encryptFieldSet = getEncryptFieldSetFromClazz(clazz);
+ if (CollUtil.isNotEmpty(encryptFieldSet)) {
+ fieldCache.put(clazz, encryptFieldSet);
+ }
+ }
+ }
+ } catch (Exception e) {
+ log.error("鍒濆鍖栨暟鎹畨鍏ㄧ紦瀛樻椂鍑洪敊:{}", e.getMessage());
+ }
+ }
+
+ /**
+ * 鑾峰緱涓�涓被鐨勫姞瀵嗗瓧娈甸泦鍚�
+ */
+ private Set<Field> getEncryptFieldSetFromClazz(Class<?> clazz) {
+ Set<Field> fieldSet = new HashSet<>();
+ // 鍒ゆ柇clazz濡傛灉鏄帴鍙�,鍐呴儴绫�,鍖垮悕绫诲氨鐩存帴杩斿洖
+ if (clazz.isInterface() || clazz.isMemberClass() || clazz.isAnonymousClass()) {
+ return fieldSet;
+ }
+ while (clazz != null) {
+ Field[] fields = clazz.getDeclaredFields();
+ fieldSet.addAll(Arrays.asList(fields));
+ clazz = clazz.getSuperclass();
+ }
+ fieldSet = fieldSet.stream().filter(field ->
+ field.isAnnotationPresent(EncryptField.class) && field.getType() == String.class)
+ .collect(Collectors.toSet());
+ for (Field field : fieldSet) {
+ field.setAccessible(true);
+ }
+ return fieldSet;
+ }
+
}
diff --git a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/CryptoFilter.java b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/CryptoFilter.java
index b43881a..9835132 100644
--- a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/CryptoFilter.java
+++ b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/CryptoFilter.java
@@ -11,14 +11,12 @@
import org.dromara.common.encrypt.annotation.ApiEncrypt;
import org.dromara.common.encrypt.properties.ApiDecryptProperties;
import org.springframework.http.HttpMethod;
-import org.springframework.http.MediaType;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.HandlerExceptionResolver;
import org.springframework.web.servlet.HandlerExecutionChain;
import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping;
import java.io.IOException;
-import java.io.PrintWriter;
/**
@@ -37,42 +35,38 @@
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
HttpServletRequest servletRequest = (HttpServletRequest) request;
HttpServletResponse servletResponse = (HttpServletResponse) response;
-
- boolean responseFlag = false;
+ // 鑾峰彇鍔犲瘑娉ㄨВ
+ ApiEncrypt apiEncrypt = this.getApiEncryptAnnotation(servletRequest);
+ boolean responseFlag = apiEncrypt != null && apiEncrypt.response();
ServletRequest requestWrapper = null;
ServletResponse responseWrapper = null;
EncryptResponseBodyWrapper responseBodyWrapper = null;
- // 鏄惁涓� json 璇锋眰
- if (StringUtils.startsWithIgnoreCase(request.getContentType(), MediaType.APPLICATION_JSON_VALUE)) {
- // 鏄惁涓� put 鎴栬�� post 璇锋眰
- if (HttpMethod.PUT.matches(servletRequest.getMethod()) || HttpMethod.POST.matches(servletRequest.getMethod())) {
- // 鏄惁瀛樺湪鍔犲瘑鏍囧ご
- String headerValue = servletRequest.getHeader(properties.getHeaderFlag());
- // 鑾峰彇鍔犲瘑娉ㄨВ
- ApiEncrypt apiEncrypt = this.getApiEncryptAnnotation(servletRequest);
- responseFlag = apiEncrypt != null && apiEncrypt.response();
- if (StringUtils.isNotBlank(headerValue)) {
- // 璇锋眰瑙e瘑
- requestWrapper = new DecryptRequestBodyWrapper(servletRequest, properties.getPrivateKey(), properties.getHeaderFlag());
- } else {
- // 鏄惁鏈夋敞瑙o紝鏈夊氨鎶ラ敊锛屾病鏈夋斁琛�
- if (ObjectUtil.isNotNull(apiEncrypt)) {
- HandlerExceptionResolver exceptionResolver = SpringUtils.getBean("handlerExceptionResolver", HandlerExceptionResolver.class);
- exceptionResolver.resolveException(
- servletRequest, servletResponse, null,
- new ServiceException("娌℃湁璁块棶鏉冮檺锛岃鑱旂郴绠$悊鍛樻巿鏉�", HttpStatus.FORBIDDEN));
- return;
- }
- }
- // 鍒ゆ柇鏄惁鍝嶅簲鍔犲瘑
- if (responseFlag) {
- responseBodyWrapper = new EncryptResponseBodyWrapper(servletResponse);
- responseWrapper = responseBodyWrapper;
+ // 鏄惁涓� put 鎴栬�� post 璇锋眰
+ if (HttpMethod.PUT.matches(servletRequest.getMethod()) || HttpMethod.POST.matches(servletRequest.getMethod())) {
+ // 鏄惁瀛樺湪鍔犲瘑鏍囧ご
+ String headerValue = servletRequest.getHeader(properties.getHeaderFlag());
+ if (StringUtils.isNotBlank(headerValue)) {
+ // 璇锋眰瑙e瘑
+ requestWrapper = new DecryptRequestBodyWrapper(servletRequest, properties.getPrivateKey(), properties.getHeaderFlag());
+ } else {
+ // 鏄惁鏈夋敞瑙o紝鏈夊氨鎶ラ敊锛屾病鏈夋斁琛�
+ if (ObjectUtil.isNotNull(apiEncrypt)) {
+ HandlerExceptionResolver exceptionResolver = SpringUtils.getBean("handlerExceptionResolver", HandlerExceptionResolver.class);
+ exceptionResolver.resolveException(
+ servletRequest, servletResponse, null,
+ new ServiceException("娌℃湁璁块棶鏉冮檺锛岃鑱旂郴绠$悊鍛樻巿鏉�", HttpStatus.FORBIDDEN));
+ return;
}
}
}
+ // 鍒ゆ柇鏄惁鍝嶅簲鍔犲瘑
+ if (responseFlag) {
+ responseBodyWrapper = new EncryptResponseBodyWrapper(servletResponse);
+ responseWrapper = responseBodyWrapper;
+ }
+
chain.doFilter(
ObjectUtil.defaultIfNull(requestWrapper, request),
ObjectUtil.defaultIfNull(responseWrapper, response));
diff --git a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/EncryptResponseBodyWrapper.java b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/EncryptResponseBodyWrapper.java
index 05cf444..c0af232 100644
--- a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/EncryptResponseBodyWrapper.java
+++ b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/filter/EncryptResponseBodyWrapper.java
@@ -76,6 +76,7 @@
String encryptPassword = EncryptUtils.encryptByRsa(encryptAes, publicKey);
// 璁剧疆鍝嶅簲澶�
+ servletResponse.addHeader("Access-Control-Expose-Headers", headerFlag);
servletResponse.setHeader(headerFlag, encryptPassword);
servletResponse.setHeader("Access-Control-Allow-Origin", "*");
servletResponse.setHeader("Access-Control-Allow-Methods", "*");
diff --git a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisDecryptInterceptor.java b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisDecryptInterceptor.java
index 7c2508f..460aa36 100644
--- a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisDecryptInterceptor.java
+++ b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisDecryptInterceptor.java
@@ -73,7 +73,11 @@
list.forEach(this::decryptHandler);
return;
}
+ // 涓嶅湪缂撳瓨涓殑绫�,灏辨槸娌℃湁鍔犲瘑娉ㄨВ鐨勭被(褰撶劧涔熸湁鍙兘鏄痶ypeAliasesPackage鍐欓敊)
Set<Field> fields = encryptorManager.getFieldCache(sourceObject.getClass());
+ if(ObjectUtil.isNull(fields)){
+ return;
+ }
try {
for (Field field : fields) {
field.set(sourceObject, this.decryptField(Convert.toStr(field.get(sourceObject)), field));
diff --git a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisEncryptInterceptor.java b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisEncryptInterceptor.java
index 152f7db..bcc2f4c 100644
--- a/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisEncryptInterceptor.java
+++ b/ruoyi-common/ruoyi-common-encrypt/src/main/java/org/dromara/common/encrypt/interceptor/MybatisEncryptInterceptor.java
@@ -82,7 +82,11 @@
list.forEach(this::encryptHandler);
return;
}
+ // 涓嶅湪缂撳瓨涓殑绫�,灏辨槸娌℃湁鍔犲瘑娉ㄨВ鐨勭被(褰撶劧涔熸湁鍙兘鏄痶ypeAliasesPackage鍐欓敊)
Set<Field> fields = encryptorManager.getFieldCache(sourceObject.getClass());
+ if(ObjectUtil.isNull(fields)){
+ return;
+ }
try {
for (Field field : fields) {
field.set(sourceObject, this.encryptField(Convert.toStr(field.get(sourceObject)), field));
diff --git a/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/annotation/CellMerge.java b/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/annotation/CellMerge.java
index bbdaaa1..6b9211b 100644
--- a/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/annotation/CellMerge.java
+++ b/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/annotation/CellMerge.java
@@ -21,4 +21,9 @@
*/
int index() default -1;
+ /**
+ * 鍚堝苟闇�瑕佷緷璧栫殑鍏朵粬瀛楁鍚嶇О
+ */
+ String[] mergeBy() default {};
+
}
diff --git a/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/CellMergeStrategy.java b/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/CellMergeStrategy.java
index bcb5be7..7c0a48b 100644
--- a/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/CellMergeStrategy.java
+++ b/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/CellMergeStrategy.java
@@ -1,8 +1,12 @@
package org.dromara.common.excel.core;
import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.util.ReflectUtil;
+import cn.hutool.core.util.StrUtil;
import com.alibaba.excel.annotation.ExcelProperty;
import com.alibaba.excel.metadata.Head;
+import com.alibaba.excel.write.handler.WorkbookWriteHandler;
+import com.alibaba.excel.write.handler.context.WorkbookWriteHandlerContext;
import com.alibaba.excel.write.merge.AbstractMergeStrategy;
import lombok.AllArgsConstructor;
import lombok.Data;
@@ -15,10 +19,7 @@
import org.dromara.common.excel.annotation.CellMerge;
import java.lang.reflect.Field;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
+import java.util.*;
/**
* 鍒楀�奸噸澶嶅悎骞剁瓥鐣�
@@ -26,7 +27,7 @@
* @author Lion Li
*/
@Slf4j
-public class CellMergeStrategy extends AbstractMergeStrategy {
+public class CellMergeStrategy extends AbstractMergeStrategy implements WorkbookWriteHandler {
private final List<CellRangeAddress> cellList;
private final boolean hasTitle;
@@ -41,13 +42,24 @@
@Override
protected void merge(Sheet sheet, Cell cell, Head head, Integer relativeRowIndex) {
- // judge the list is not null
- if (CollUtil.isNotEmpty(cellList)) {
- // the judge is necessary
- if (cell.getRowIndex() == rowIndex && cell.getColumnIndex() == 0) {
- for (CellRangeAddress item : cellList) {
- sheet.addMergedRegion(item);
+ //鍗曞厓鏍煎啓鍏ヤ簡,閬嶅巻鍚堝苟鍖哄煙,濡傛灉璇ell鍦ㄥ尯鍩熷唴,浣嗛潪棣栬,鍒欐竻绌�
+ final int rowIndex = cell.getRowIndex();
+ if (CollUtil.isNotEmpty(cellList)){
+ for (CellRangeAddress cellAddresses : cellList) {
+ final int firstRow = cellAddresses.getFirstRow();
+ if (cellAddresses.isInRange(cell) && rowIndex != firstRow){
+ cell.setBlank();
}
+ }
+ }
+ }
+
+ @Override
+ public void afterWorkbookDispose(final WorkbookWriteHandlerContext context) {
+ //褰撳墠琛ㄦ牸鍐欏畬鍚庯紝缁熶竴鍐欏叆
+ if (CollUtil.isNotEmpty(cellList)){
+ for (CellRangeAddress item : cellList) {
+ context.getWriteContext().writeSheetHolder().getSheet().addMergedRegion(item);
}
}
}
@@ -93,35 +105,15 @@
// 绌哄�艰烦杩囦笉鍚堝苟
continue;
}
+
if (!cellValue.equals(val)) {
- if (i - repeatCell.getCurrent() > 1) {
+ if ((i - repeatCell.getCurrent() > 1) && isMerge(list, i, field)) {
cellList.add(new CellRangeAddress(repeatCell.getCurrent() + rowIndex, i + rowIndex - 1, colNum, colNum));
}
map.put(field, new RepeatCell(val, i));
- } else if (j == 0) {
- if (i == list.size() - 1) {
- if (i > repeatCell.getCurrent()) {
- cellList.add(new CellRangeAddress(repeatCell.getCurrent() + rowIndex, i + rowIndex, colNum, colNum));
- }
- }
- } else {
- // 鍒ゆ柇鍓嶉潰鐨勬槸鍚﹀悎骞朵簡
- RepeatCell firstCell = map.get(mergeFields.get(0));
- if (repeatCell.getCurrent() != firstCell.getCurrent()) {
- if (i == list.size() - 1) {
- if (i > repeatCell.getCurrent()) {
- cellList.add(new CellRangeAddress(repeatCell.getCurrent() + rowIndex, i + rowIndex, colNum, colNum));
- }
- } else if (repeatCell.getCurrent() < firstCell.getCurrent()) {
- if (i - repeatCell.getCurrent() > 1) {
- cellList.add(new CellRangeAddress(repeatCell.getCurrent() + rowIndex, i + rowIndex - 1, colNum, colNum));
- }
- map.put(field, new RepeatCell(val, i));
- }
- } else if (i == list.size() - 1) {
- if (i > repeatCell.getCurrent()) {
- cellList.add(new CellRangeAddress(repeatCell.getCurrent() + rowIndex, i + rowIndex, colNum, colNum));
- }
+ } else if (i == list.size() - 1) {
+ if (i > repeatCell.getCurrent() && isMerge(list, i, field)) {
+ cellList.add(new CellRangeAddress(repeatCell.getCurrent() + rowIndex, i + rowIndex, colNum, colNum));
}
}
}
@@ -130,6 +122,24 @@
return cellList;
}
+ private boolean isMerge(List<?> list, int i, Field field) {
+ boolean isMerge = true;
+ CellMerge cm = field.getAnnotation(CellMerge.class);
+ final String[] mergeBy = cm.mergeBy();
+ if (StrUtil.isAllNotBlank(mergeBy)) {
+ //姣斿褰撳墠list(i)鍜宭ist(i - 1)鐨勫悇涓睘鎬у�间竴涓�姣斿 濡傛灉鍏ㄤ负鐪� 鍒欎负鐪�
+ for (String fieldName : mergeBy) {
+ final Object valCurrent = ReflectUtil.getFieldValue(list.get(i), fieldName);
+ final Object valPre = ReflectUtil.getFieldValue(list.get(i - 1), fieldName);
+ if (!Objects.equals(valPre, valCurrent)) {
+ //渚濊禆瀛楁濡傛湁浠讳竴涓嶇瓑鍊�,鍒欐爣璁颁负涓嶅彲鍚堝苟
+ isMerge = false;
+ }
+ }
+ }
+ return isMerge;
+ }
+
@Data
@AllArgsConstructor
static class RepeatCell {
diff --git a/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/ExcelDownHandler.java b/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/ExcelDownHandler.java
index 3b791ea..b3f68ed 100644
--- a/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/ExcelDownHandler.java
+++ b/ruoyi-common/ruoyi-common-excel/src/main/java/org/dromara/common/excel/core/ExcelDownHandler.java
@@ -20,6 +20,7 @@
import org.dromara.common.core.service.DictService;
import org.dromara.common.core.utils.SpringUtils;
import org.dromara.common.core.utils.StreamUtils;
+import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.excel.annotation.ExcelDictFormat;
import org.dromara.common.excel.annotation.ExcelEnumFormat;
@@ -99,15 +100,16 @@
ExcelDictFormat format = field.getDeclaredAnnotation(ExcelDictFormat.class);
String dictType = format.dictType();
String converterExp = format.readConverterExp();
- if (StrUtil.isNotBlank(dictType)) {
+ if (StringUtils.isNotBlank(dictType)) {
// 濡傛灉浼犻�掍簡瀛楀吀鍚嶏紝鍒欎緷鎹瓧鍏稿缓绔嬩笅鎷�
Collection<String> values = Optional.ofNullable(dictService.getAllDictByDictType(dictType))
.orElseThrow(() -> new ServiceException(String.format("瀛楀吀 %s 涓嶅瓨鍦�", dictType)))
.values();
options = new ArrayList<>(values);
- } else if (StrUtil.isNotBlank(converterExp)) {
+ } else if (StringUtils.isNotBlank(converterExp)) {
// 濡傛灉鎸囧畾浜嗙‘鍒囩殑鍊硷紝鍒欑洿鎺ヨВ鏋愮‘鍒囩殑鍊�
- options = StrUtil.split(converterExp, format.separator(), true, true);
+ List<String> strList = StringUtils.splitList(converterExp, format.separator());
+ options = StreamUtils.toList(strList, s -> StringUtils.split(s, "=")[1]);
}
} else if (field.isAnnotationPresent(ExcelEnumFormat.class)) {
// 鍚﹀垯濡傛灉鎸囧畾浜咢ExcelEnumFormat锛屽垯浣跨敤鏋氫妇鐨勯�昏緫
diff --git a/ruoyi-common/ruoyi-common-idempotent/src/main/java/org/dromara/common/idempotent/aspectj/RepeatSubmitAspect.java b/ruoyi-common/ruoyi-common-idempotent/src/main/java/org/dromara/common/idempotent/aspectj/RepeatSubmitAspect.java
index 016fe0f..5a27e91 100644
--- a/ruoyi-common/ruoyi-common-idempotent/src/main/java/org/dromara/common/idempotent/aspectj/RepeatSubmitAspect.java
+++ b/ruoyi-common/ruoyi-common-idempotent/src/main/java/org/dromara/common/idempotent/aspectj/RepeatSubmitAspect.java
@@ -4,6 +4,13 @@
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.crypto.SecureUtil;
+import jakarta.servlet.http.HttpServletRequest;
+import jakarta.servlet.http.HttpServletResponse;
+import org.aspectj.lang.JoinPoint;
+import org.aspectj.lang.annotation.AfterReturning;
+import org.aspectj.lang.annotation.AfterThrowing;
+import org.aspectj.lang.annotation.Aspect;
+import org.aspectj.lang.annotation.Before;
import org.dromara.common.core.constant.GlobalConstants;
import org.dromara.common.core.domain.R;
import org.dromara.common.core.exception.ServiceException;
@@ -13,13 +20,6 @@
import org.dromara.common.idempotent.annotation.RepeatSubmit;
import org.dromara.common.json.utils.JsonUtils;
import org.dromara.common.redis.utils.RedisUtils;
-import jakarta.servlet.http.HttpServletRequest;
-import jakarta.servlet.http.HttpServletResponse;
-import org.aspectj.lang.JoinPoint;
-import org.aspectj.lang.annotation.AfterReturning;
-import org.aspectj.lang.annotation.AfterThrowing;
-import org.aspectj.lang.annotation.Aspect;
-import org.aspectj.lang.annotation.Before;
import org.springframework.validation.BindingResult;
import org.springframework.web.multipart.MultipartFile;
@@ -127,7 +127,7 @@
public boolean isFilterObject(final Object o) {
Class<?> clazz = o.getClass();
if (clazz.isArray()) {
- return clazz.getComponentType().isAssignableFrom(MultipartFile.class);
+ return MultipartFile.class.isAssignableFrom(clazz.getComponentType());
} else if (Collection.class.isAssignableFrom(clazz)) {
Collection collection = (Collection) o;
for (Object value : collection) {
diff --git a/ruoyi-common/ruoyi-common-job/pom.xml b/ruoyi-common/ruoyi-common-job/pom.xml
index 1a6e729..3a4a0cb 100644
--- a/ruoyi-common/ruoyi-common-job/pom.xml
+++ b/ruoyi-common/ruoyi-common-job/pom.xml
@@ -22,20 +22,14 @@
<artifactId>spring-boot-autoconfigure</artifactId>
</dependency>
- <!--PowerJob-->
+ <!-- SnailJob client -->
<dependency>
- <groupId>tech.powerjob</groupId>
- <artifactId>powerjob-worker-spring-boot-starter</artifactId>
- <exclusions>
- <exclusion>
- <artifactId>powerjob-remote-impl-akka</artifactId>
- <groupId>tech.powerjob</groupId>
- </exclusion>
- </exclusions>
+ <groupId>com.aizuda</groupId>
+ <artifactId>snail-job-client-starter</artifactId>
</dependency>
<dependency>
- <groupId>tech.powerjob</groupId>
- <artifactId>powerjob-official-processors</artifactId>
+ <groupId>com.aizuda</groupId>
+ <artifactId>snail-job-client-job-core</artifactId>
</dependency>
<dependency>
diff --git a/ruoyi-common/ruoyi-common-job/src/main/java/org/dromara/common/job/config/PowerJobConfig.java b/ruoyi-common/ruoyi-common-job/src/main/java/org/dromara/common/job/config/PowerJobConfig.java
deleted file mode 100644
index 67208c0..0000000
--- a/ruoyi-common/ruoyi-common-job/src/main/java/org/dromara/common/job/config/PowerJobConfig.java
+++ /dev/null
@@ -1,21 +0,0 @@
-package org.dromara.common.job.config;
-
-import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
-import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
-import org.springframework.context.annotation.Configuration;
-import org.springframework.scheduling.annotation.EnableScheduling;
-import tech.powerjob.worker.PowerJobWorker;
-
-/**
- * 鍚姩瀹氭椂浠诲姟
- * @author yhan219
- * @since 2023/6/2
- */
-@Configuration
-@ConditionalOnBean(PowerJobWorker.class)
-@ConditionalOnProperty(prefix = "powerjob.worker", name = "enabled", havingValue = "true")
-@EnableScheduling
-public class PowerJobConfig {
-
-
-}
diff --git a/ruoyi-common/ruoyi-common-job/src/main/java/org/dromara/common/job/config/SnailJobConfig.java b/ruoyi-common/ruoyi-common-job/src/main/java/org/dromara/common/job/config/SnailJobConfig.java
new file mode 100644
index 0000000..d671f0e
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-job/src/main/java/org/dromara/common/job/config/SnailJobConfig.java
@@ -0,0 +1,37 @@
+package org.dromara.common.job.config;
+
+import ch.qos.logback.classic.Logger;
+import ch.qos.logback.classic.LoggerContext;
+import ch.qos.logback.classic.spi.ILoggingEvent;
+import com.aizuda.snailjob.client.common.appender.SnailLogbackAppender;
+import com.aizuda.snailjob.client.common.event.SnailClientStartingEvent;
+import com.aizuda.snailjob.client.starter.EnableSnailJob;
+import org.slf4j.LoggerFactory;
+import org.springframework.boot.autoconfigure.AutoConfiguration;
+import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
+import org.springframework.context.event.EventListener;
+import org.springframework.scheduling.annotation.EnableScheduling;
+
+/**
+ * 鍚姩瀹氭椂浠诲姟
+ *
+ * @author opensnail
+ * @date 2024-05-17
+ */
+@AutoConfiguration
+@ConditionalOnProperty(prefix = "snail-job", name = "enabled", havingValue = "true")
+@EnableScheduling
+@EnableSnailJob(group = "${snail-job.group-name}")
+public class SnailJobConfig {
+
+ @EventListener(SnailClientStartingEvent.class)
+ public void onStarting(SnailClientStartingEvent event) {
+ LoggerContext lc = (LoggerContext) LoggerFactory.getILoggerFactory();
+ SnailLogbackAppender<ILoggingEvent> ca = new SnailLogbackAppender<>();
+ ca.setName("snail_log_appender");
+ ca.start();
+ Logger rootLogger = lc.getLogger(Logger.ROOT_LOGGER_NAME);
+ rootLogger.addAppender(ca);
+ }
+
+}
diff --git a/ruoyi-common/ruoyi-common-job/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports b/ruoyi-common/ruoyi-common-job/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
new file mode 100644
index 0000000..3aa1881
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-job/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
@@ -0,0 +1 @@
+org.dromara.common.job.config.SnailJobConfig
diff --git a/ruoyi-common/ruoyi-common-json/src/main/java/org/dromara/common/json/utils/JsonUtils.java b/ruoyi-common/ruoyi-common-json/src/main/java/org/dromara/common/json/utils/JsonUtils.java
index 42af8da..65c2faa 100644
--- a/ruoyi-common/ruoyi-common-json/src/main/java/org/dromara/common/json/utils/JsonUtils.java
+++ b/ruoyi-common/ruoyi-common-json/src/main/java/org/dromara/common/json/utils/JsonUtils.java
@@ -7,10 +7,10 @@
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.exc.MismatchedInputException;
-import org.dromara.common.core.utils.SpringUtils;
-import org.dromara.common.core.utils.StringUtils;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
+import org.dromara.common.core.utils.SpringUtils;
+import org.dromara.common.core.utils.StringUtils;
import java.io.IOException;
import java.util.ArrayList;
@@ -30,6 +30,13 @@
return OBJECT_MAPPER;
}
+ /**
+ * 灏嗗璞¤浆鎹负JSON鏍煎紡鐨勫瓧绗︿覆
+ *
+ * @param object 瑕佽浆鎹㈢殑瀵硅薄
+ * @return JSON鏍煎紡鐨勫瓧绗︿覆锛屽鏋滃璞′负null锛屽垯杩斿洖null
+ * @throws RuntimeException 濡傛灉杞崲杩囩▼涓彂鐢烰SON澶勭悊寮傚父锛屽垯鎶涘嚭杩愯鏃跺紓甯�
+ */
public static String toJsonString(Object object) {
if (ObjectUtil.isNull(object)) {
return null;
@@ -41,6 +48,15 @@
}
}
+ /**
+ * 灏咼SON鏍煎紡鐨勫瓧绗︿覆杞崲涓烘寚瀹氱被鍨嬬殑瀵硅薄
+ *
+ * @param text JSON鏍煎紡鐨勫瓧绗︿覆
+ * @param clazz 瑕佽浆鎹㈢殑鐩爣瀵硅薄绫诲瀷
+ * @param <T> 鐩爣瀵硅薄鐨勬硾鍨嬬被鍨�
+ * @return 杞崲鍚庣殑瀵硅薄锛屽鏋滃瓧绗︿覆涓虹┖鍒欒繑鍥瀗ull
+ * @throws RuntimeException 濡傛灉杞崲杩囩▼涓彂鐢烮O寮傚父锛屽垯鎶涘嚭杩愯鏃跺紓甯�
+ */
public static <T> T parseObject(String text, Class<T> clazz) {
if (StringUtils.isEmpty(text)) {
return null;
@@ -52,6 +68,15 @@
}
}
+ /**
+ * 灏嗗瓧鑺傛暟缁勮浆鎹负鎸囧畾绫诲瀷鐨勫璞�
+ *
+ * @param bytes 瀛楄妭鏁扮粍
+ * @param clazz 瑕佽浆鎹㈢殑鐩爣瀵硅薄绫诲瀷
+ * @param <T> 鐩爣瀵硅薄鐨勬硾鍨嬬被鍨�
+ * @return 杞崲鍚庣殑瀵硅薄锛屽鏋滃瓧鑺傛暟缁勪负绌哄垯杩斿洖null
+ * @throws RuntimeException 濡傛灉杞崲杩囩▼涓彂鐢烮O寮傚父锛屽垯鎶涘嚭杩愯鏃跺紓甯�
+ */
public static <T> T parseObject(byte[] bytes, Class<T> clazz) {
if (ArrayUtil.isEmpty(bytes)) {
return null;
@@ -63,6 +88,15 @@
}
}
+ /**
+ * 灏咼SON鏍煎紡鐨勫瓧绗︿覆杞崲涓烘寚瀹氱被鍨嬬殑瀵硅薄锛屾敮鎸佸鏉傜被鍨�
+ *
+ * @param text JSON鏍煎紡鐨勫瓧绗︿覆
+ * @param typeReference 鎸囧畾绫诲瀷鐨凾ypeReference瀵硅薄
+ * @param <T> 鐩爣瀵硅薄鐨勬硾鍨嬬被鍨�
+ * @return 杞崲鍚庣殑瀵硅薄锛屽鏋滃瓧绗︿覆涓虹┖鍒欒繑鍥瀗ull
+ * @throws RuntimeException 濡傛灉杞崲杩囩▼涓彂鐢烮O寮傚父锛屽垯鎶涘嚭杩愯鏃跺紓甯�
+ */
public static <T> T parseObject(String text, TypeReference<T> typeReference) {
if (StringUtils.isBlank(text)) {
return null;
@@ -74,6 +108,13 @@
}
}
+ /**
+ * 灏咼SON鏍煎紡鐨勫瓧绗︿覆杞崲涓篋ict瀵硅薄
+ *
+ * @param text JSON鏍煎紡鐨勫瓧绗︿覆
+ * @return 杞崲鍚庣殑Dict瀵硅薄锛屽鏋滃瓧绗︿覆涓虹┖鎴栬�呬笉鏄疛SON鏍煎紡鍒欒繑鍥瀗ull
+ * @throws RuntimeException 濡傛灉杞崲杩囩▼涓彂鐢烮O寮傚父锛屽垯鎶涘嚭杩愯鏃跺紓甯�
+ */
public static Dict parseMap(String text) {
if (StringUtils.isBlank(text)) {
return null;
@@ -88,6 +129,13 @@
}
}
+ /**
+ * 灏咼SON鏍煎紡鐨勫瓧绗︿覆杞崲涓篋ict瀵硅薄鐨勫垪琛�
+ *
+ * @param text JSON鏍煎紡鐨勫瓧绗︿覆
+ * @return 杞崲鍚庣殑Dict瀵硅薄鐨勫垪琛紝濡傛灉瀛楃涓蹭负绌哄垯杩斿洖null
+ * @throws RuntimeException 濡傛灉杞崲杩囩▼涓彂鐢烮O寮傚父锛屽垯鎶涘嚭杩愯鏃跺紓甯�
+ */
public static List<Dict> parseArrayMap(String text) {
if (StringUtils.isBlank(text)) {
return null;
@@ -99,6 +147,15 @@
}
}
+ /**
+ * 灏咼SON鏍煎紡鐨勫瓧绗︿覆杞崲涓烘寚瀹氱被鍨嬪璞$殑鍒楄〃
+ *
+ * @param text JSON鏍煎紡鐨勫瓧绗︿覆
+ * @param clazz 瑕佽浆鎹㈢殑鐩爣瀵硅薄绫诲瀷
+ * @param <T> 鐩爣瀵硅薄鐨勬硾鍨嬬被鍨�
+ * @return 杞崲鍚庣殑瀵硅薄鐨勫垪琛紝濡傛灉瀛楃涓蹭负绌哄垯杩斿洖绌哄垪琛�
+ * @throws RuntimeException 濡傛灉杞崲杩囩▼涓彂鐢烮O寮傚父锛屽垯鎶涘嚭杩愯鏃跺紓甯�
+ */
public static <T> List<T> parseArray(String text, Class<T> clazz) {
if (StringUtils.isEmpty(text)) {
return new ArrayList<>();
diff --git a/ruoyi-common/ruoyi-common-log/pom.xml b/ruoyi-common/ruoyi-common-log/pom.xml
index 28bd530..1e2b33b 100644
--- a/ruoyi-common/ruoyi-common-log/pom.xml
+++ b/ruoyi-common/ruoyi-common-log/pom.xml
@@ -27,11 +27,6 @@
<artifactId>ruoyi-common-json</artifactId>
</dependency>
- <dependency>
- <groupId>com.alibaba</groupId>
- <artifactId>transmittable-thread-local</artifactId>
- </dependency>
-
</dependencies>
</project>
diff --git a/ruoyi-common/ruoyi-common-log/src/main/java/org/dromara/common/log/aspect/LogAspect.java b/ruoyi-common/ruoyi-common-log/src/main/java/org/dromara/common/log/aspect/LogAspect.java
index e98f4f7..8724072 100644
--- a/ruoyi-common/ruoyi-common-log/src/main/java/org/dromara/common/log/aspect/LogAspect.java
+++ b/ruoyi-common/ruoyi-common-log/src/main/java/org/dromara/common/log/aspect/LogAspect.java
@@ -4,16 +4,6 @@
import cn.hutool.core.map.MapUtil;
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.util.ObjectUtil;
-import com.alibaba.ttl.TransmittableThreadLocal;
-import org.dromara.common.core.domain.model.LoginUser;
-import org.dromara.common.core.utils.ServletUtils;
-import org.dromara.common.core.utils.SpringUtils;
-import org.dromara.common.core.utils.StringUtils;
-import org.dromara.common.json.utils.JsonUtils;
-import org.dromara.common.log.annotation.Log;
-import org.dromara.common.log.enums.BusinessStatus;
-import org.dromara.common.log.event.OperLogEvent;
-import org.dromara.common.satoken.utils.LoginHelper;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
@@ -23,6 +13,15 @@
import org.aspectj.lang.annotation.AfterThrowing;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
+import org.dromara.common.core.domain.model.LoginUser;
+import org.dromara.common.core.utils.ServletUtils;
+import org.dromara.common.core.utils.SpringUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.json.utils.JsonUtils;
+import org.dromara.common.log.annotation.Log;
+import org.dromara.common.log.enums.BusinessStatus;
+import org.dromara.common.log.event.OperLogEvent;
+import org.dromara.common.satoken.utils.LoginHelper;
import org.springframework.boot.autoconfigure.AutoConfiguration;
import org.springframework.http.HttpMethod;
import org.springframework.validation.BindingResult;
@@ -49,9 +48,9 @@
/**
- * 璁$畻鎿嶄綔娑堣�楁椂闂�
+ * 璁℃椂 key
*/
- private static final ThreadLocal<StopWatch> TIME_THREADLOCAL = new TransmittableThreadLocal<>();
+ private static final ThreadLocal<StopWatch> KEY_CACHE = new ThreadLocal<>();
/**
* 澶勭悊璇锋眰鍓嶆墽琛�
@@ -59,7 +58,7 @@
@Before(value = "@annotation(controllerLog)")
public void boBefore(JoinPoint joinPoint, Log controllerLog) {
StopWatch stopWatch = new StopWatch();
- TIME_THREADLOCAL.set(stopWatch);
+ KEY_CACHE.set(stopWatch);
stopWatch.start();
}
@@ -112,7 +111,7 @@
// 澶勭悊璁剧疆娉ㄨВ涓婄殑鍙傛暟
getControllerMethodDescription(joinPoint, controllerLog, operLog, jsonResult);
// 璁剧疆娑堣�楁椂闂�
- StopWatch stopWatch = TIME_THREADLOCAL.get();
+ StopWatch stopWatch = KEY_CACHE.get();
stopWatch.stop();
operLog.setCostTime(stopWatch.getTime());
// 鍙戝竷浜嬩欢淇濆瓨鏁版嵁搴�
@@ -122,7 +121,7 @@
log.error("寮傚父淇℃伅:{}", exp.getMessage());
exp.printStackTrace();
} finally {
- TIME_THREADLOCAL.remove();
+ KEY_CACHE.remove();
}
}
@@ -204,7 +203,7 @@
public boolean isFilterObject(final Object o) {
Class<?> clazz = o.getClass();
if (clazz.isArray()) {
- return clazz.getComponentType().isAssignableFrom(MultipartFile.class);
+ return MultipartFile.class.isAssignableFrom(clazz.getComponentType());
} else if (Collection.class.isAssignableFrom(clazz)) {
Collection collection = (Collection) o;
for (Object value : collection) {
diff --git a/ruoyi-common/ruoyi-common-mybatis/pom.xml b/ruoyi-common/ruoyi-common-mybatis/pom.xml
index 2088b54..a58064a 100644
--- a/ruoyi-common/ruoyi-common-mybatis/pom.xml
+++ b/ruoyi-common/ruoyi-common-mybatis/pom.xml
@@ -33,19 +33,8 @@
</dependency>
<dependency>
- <groupId>org.mybatis.spring.boot</groupId>
- <artifactId>mybatis-spring-boot-starter</artifactId>
- </dependency>
-
- <dependency>
<groupId>com.baomidou</groupId>
- <artifactId>mybatis-plus-boot-starter</artifactId>
- <exclusions>
- <exclusion>
- <groupId>org.mybatis</groupId>
- <artifactId>mybatis-spring</artifactId>
- </exclusion>
- </exclusions>
+ <artifactId>mybatis-plus-spring-boot3-starter</artifactId>
</dependency>
<!-- sql鎬ц兘鍒嗘瀽鎻掍欢 -->
diff --git a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/config/MybatisPlusConfig.java b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/config/MybatisPlusConfig.java
index 1689e3c..0bc5b66 100644
--- a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/config/MybatisPlusConfig.java
+++ b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/config/MybatisPlusConfig.java
@@ -1,26 +1,23 @@
package org.dromara.common.mybatis.config;
import cn.hutool.core.net.NetUtil;
-import com.baomidou.mybatisplus.autoconfigure.DdlApplicationRunner;
-import com.baomidou.mybatisplus.autoconfigure.MybatisPlusAutoConfiguration;
import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
import com.baomidou.mybatisplus.core.incrementer.DefaultIdentifierGenerator;
import com.baomidou.mybatisplus.core.incrementer.IdentifierGenerator;
-import com.baomidou.mybatisplus.extension.ddl.IDdl;
import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.OptimisticLockerInnerInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.PaginationInnerInterceptor;
+import com.baomidou.mybatisplus.extension.plugins.inner.TenantLineInnerInterceptor;
import org.dromara.common.core.factory.YmlPropertySourceFactory;
+import org.dromara.common.core.utils.SpringUtils;
import org.dromara.common.mybatis.handler.InjectionMetaObjectHandler;
+import org.dromara.common.mybatis.handler.MybatisExceptionHandler;
import org.dromara.common.mybatis.interceptor.PlusDataPermissionInterceptor;
import org.mybatis.spring.annotation.MapperScan;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.autoconfigure.AutoConfiguration;
+import org.springframework.beans.BeansException;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.PropertySource;
import org.springframework.transaction.annotation.EnableTransactionManagement;
-
-import java.util.List;
/**
* mybatis-plus閰嶇疆绫�(涓嬫柟娉ㄩ噴鏈夋彃浠朵粙缁�)
@@ -28,7 +25,6 @@
* @author Lion Li
*/
@EnableTransactionManagement(proxyTargetClass = true)
-@AutoConfiguration(before = MybatisPlusAutoConfiguration.class)
@MapperScan("${mybatis-plus.mapperPackage}")
@PropertySource(value = "classpath:common-mybatis.yml", factory = YmlPropertySourceFactory.class)
public class MybatisPlusConfig {
@@ -36,6 +32,12 @@
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor() {
MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
+ // 澶氱鎴锋彃浠� 蹇呴』鏀惧埌绗竴浣�
+ try {
+ TenantLineInnerInterceptor tenant = SpringUtils.getBean(TenantLineInnerInterceptor.class);
+ interceptor.addInnerInterceptor(tenant);
+ } catch (BeansException ignore) {
+ }
// 鏁版嵁鏉冮檺澶勭悊
interceptor.addInnerInterceptor(dataPermissionInterceptor());
// 鍒嗛〉鎻掍欢
@@ -49,7 +51,7 @@
* 鏁版嵁鏉冮檺鎷︽埅鍣�
*/
public PlusDataPermissionInterceptor dataPermissionInterceptor() {
- return new PlusDataPermissionInterceptor();
+ return new PlusDataPermissionInterceptor(SpringUtils.getProperty("mybatis-plus.mapperPackage"));
}
/**
@@ -57,8 +59,6 @@
*/
public PaginationInnerInterceptor paginationInnerInterceptor() {
PaginationInnerInterceptor paginationInnerInterceptor = new PaginationInnerInterceptor();
- // 璁剧疆鏈�澶у崟椤甸檺鍒舵暟閲忥紝榛樿 500 鏉★紝-1 涓嶅彈闄愬埗
- paginationInnerInterceptor.setMaxLimit(-1L);
// 鍒嗛〉鍚堢悊鍖�
paginationInnerInterceptor.setOverflow(true);
return paginationInnerInterceptor;
@@ -89,6 +89,14 @@
}
/**
+ * 寮傚父澶勭悊鍣�
+ */
+ @Bean
+ public MybatisExceptionHandler mybatisExceptionHandler() {
+ return new MybatisExceptionHandler();
+ }
+
+ /**
* PaginationInnerInterceptor 鍒嗛〉鎻掍欢锛岃嚜鍔ㄨ瘑鍒暟鎹簱绫诲瀷
* https://baomidou.com/pages/97710a/
* OptimisticLockerInnerInterceptor 涔愯閿佹彃浠�
@@ -107,10 +115,5 @@
* DynamicTableNameInnerInterceptor 鍔ㄦ�佽〃鍚嶆彃浠�
* https://baomidou.com/pages/2a45ff/
*/
-
- @Bean
- public DdlApplicationRunner ddlApplicationRunner(@Autowired(required = false) List<IDdl> ddlList) {
- return new DdlApplicationRunner(ddlList);
- }
}
diff --git a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/mapper/BaseMapperPlus.java b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/mapper/BaseMapperPlus.java
index 9018a79..08723f6 100644
--- a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/mapper/BaseMapperPlus.java
+++ b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/mapper/BaseMapperPlus.java
@@ -35,7 +35,6 @@
Log log = LogFactory.getLog(BaseMapperPlus.class);
default Class<V> currentVoClass() {
- GenericTypeUtils.resolveTypeArguments(this.getClass(), BaseMapperPlus.class);
return (Class<V>) GenericTypeUtils.resolveTypeArguments(this.getClass(), BaseMapperPlus.class)[1];
}
@@ -145,11 +144,22 @@
return selectVoOne(wrapper, this.currentVoClass());
}
+ default V selectVoOne(Wrapper<T> wrapper, boolean throwEx) {
+ return selectVoOne(wrapper, this.currentVoClass(), throwEx);
+ }
+
/**
* 鏍规嵁 entity 鏉′欢锛屾煡璇竴鏉¤褰�
*/
default <C> C selectVoOne(Wrapper<T> wrapper, Class<C> voClass) {
- T obj = this.selectOne(wrapper);
+ return selectVoOne(wrapper, voClass, true);
+ }
+
+ /**
+ * 鏍规嵁 entity 鏉′欢锛屾煡璇竴鏉¤褰�
+ */
+ default <C> C selectVoOne(Wrapper<T> wrapper, Class<C> voClass, boolean throwEx) {
+ T obj = this.selectOne(wrapper, throwEx);
if (ObjectUtil.isNull(obj)) {
return null;
}
diff --git a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/page/PageQuery.java b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/page/PageQuery.java
index 8ef4a57..40b7530 100644
--- a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/page/PageQuery.java
+++ b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/core/page/PageQuery.java
@@ -111,4 +111,8 @@
return list;
}
+ public Integer getFirstNum() {
+ return (pageNum - 1) * pageSize;
+ }
+
}
diff --git a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/InjectionMetaObjectHandler.java b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/InjectionMetaObjectHandler.java
index 63653de..a66908f 100644
--- a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/InjectionMetaObjectHandler.java
+++ b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/InjectionMetaObjectHandler.java
@@ -29,16 +29,17 @@
? baseEntity.getCreateTime() : new Date();
baseEntity.setCreateTime(current);
baseEntity.setUpdateTime(current);
- LoginUser loginUser = getLoginUser();
- if (ObjectUtil.isNotNull(loginUser)) {
- Long userId = ObjectUtil.isNotNull(baseEntity.getCreateBy())
- ? baseEntity.getCreateBy() : loginUser.getUserId();
- // 褰撳墠宸茬櫥褰� 涓� 鍒涘缓浜轰负绌� 鍒欏~鍏�
- baseEntity.setCreateBy(userId);
- // 褰撳墠宸茬櫥褰� 涓� 鏇存柊浜轰负绌� 鍒欏~鍏�
- baseEntity.setUpdateBy(userId);
- baseEntity.setCreateDept(ObjectUtil.isNotNull(baseEntity.getCreateDept())
- ? baseEntity.getCreateDept() : loginUser.getDeptId());
+ if (ObjectUtil.isNull(baseEntity.getCreateBy())) {
+ LoginUser loginUser = getLoginUser();
+ if (ObjectUtil.isNotNull(loginUser)) {
+ Long userId = loginUser.getUserId();
+ // 褰撳墠宸茬櫥褰� 涓� 鍒涘缓浜轰负绌� 鍒欏~鍏�
+ baseEntity.setCreateBy(userId);
+ // 褰撳墠宸茬櫥褰� 涓� 鏇存柊浜轰负绌� 鍒欏~鍏�
+ baseEntity.setUpdateBy(userId);
+ baseEntity.setCreateDept(ObjectUtil.isNotNull(baseEntity.getCreateDept())
+ ? baseEntity.getCreateDept() : loginUser.getDeptId());
+ }
}
}
} catch (Exception e) {
@@ -53,11 +54,12 @@
Date current = new Date();
// 鏇存柊鏃堕棿濉厖(涓嶇涓轰笉涓虹┖)
baseEntity.setUpdateTime(current);
- LoginUser loginUser = getLoginUser();
// 褰撳墠宸茬櫥褰� 鏇存柊浜哄~鍏�(涓嶇涓轰笉涓虹┖)
- if (ObjectUtil.isNotNull(loginUser)) {
- baseEntity.setUpdateBy(loginUser.getUserId());
+ Long userId = LoginHelper.getUserId();
+ if (ObjectUtil.isNotNull(userId)) {
+ baseEntity.setUpdateBy(userId);
}
+
}
} catch (Exception e) {
throw new ServiceException("鑷姩娉ㄥ叆寮傚父 => " + e.getMessage(), HttpStatus.HTTP_UNAUTHORIZED);
diff --git a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/MybatisExceptionHandler.java b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/MybatisExceptionHandler.java
index c517fa7..ec3ee0d 100644
--- a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/MybatisExceptionHandler.java
+++ b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/MybatisExceptionHandler.java
@@ -2,6 +2,7 @@
import org.dromara.common.core.domain.R;
import lombok.extern.slf4j.Slf4j;
+import org.dromara.common.core.utils.StringUtils;
import org.mybatis.spring.MyBatisSystemException;
import org.springframework.dao.DuplicateKeyException;
import org.springframework.web.bind.annotation.ExceptionHandler;
@@ -35,7 +36,7 @@
public R<Void> handleCannotFindDataSourceException(MyBatisSystemException e, HttpServletRequest request) {
String requestURI = request.getRequestURI();
String message = e.getMessage();
- if ("CannotFindDataSourceException".contains(message)) {
+ if (StringUtils.contains("CannotFindDataSourceException", message)) {
log.error("璇锋眰鍦板潃'{}', 鏈壘鍒版暟鎹簮", requestURI);
return R.fail("鏈壘鍒版暟鎹簮锛岃鑱旂郴绠$悊鍛樼‘璁�");
}
diff --git a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/PlusDataPermissionHandler.java b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/PlusDataPermissionHandler.java
index 6ddaa24..7d7fd84 100644
--- a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/PlusDataPermissionHandler.java
+++ b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/handler/PlusDataPermissionHandler.java
@@ -2,7 +2,6 @@
import cn.hutool.core.annotation.AnnotationUtil;
import cn.hutool.core.collection.CollUtil;
-import cn.hutool.core.util.ClassUtil;
import cn.hutool.core.util.ObjectUtil;
import lombok.extern.slf4j.Slf4j;
import net.sf.jsqlparser.JSQLParserException;
@@ -10,6 +9,7 @@
import net.sf.jsqlparser.expression.Parenthesis;
import net.sf.jsqlparser.expression.operators.conditional.AndExpression;
import net.sf.jsqlparser.parser.CCJSqlParserUtil;
+import org.apache.ibatis.io.Resources;
import org.dromara.common.core.domain.dto.RoleDTO;
import org.dromara.common.core.domain.model.LoginUser;
import org.dromara.common.core.exception.ServiceException;
@@ -21,16 +21,26 @@
import org.dromara.common.mybatis.enums.DataScopeType;
import org.dromara.common.mybatis.helper.DataPermissionHelper;
import org.dromara.common.satoken.utils.LoginHelper;
+import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.expression.BeanFactoryResolver;
+import org.springframework.core.io.Resource;
+import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
+import org.springframework.core.io.support.ResourcePatternResolver;
+import org.springframework.core.type.ClassMetadata;
+import org.springframework.core.type.classreading.CachingMetadataReaderFactory;
import org.springframework.expression.BeanResolver;
import org.springframework.expression.ExpressionParser;
import org.springframework.expression.ParserContext;
import org.springframework.expression.common.TemplateParserContext;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.expression.spel.support.StandardEvaluationContext;
+import org.springframework.util.ClassUtils;
import java.lang.reflect.Method;
-import java.util.*;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.function.Function;
@@ -58,9 +68,13 @@
*/
private final BeanResolver beanResolver = new BeanFactoryResolver(SpringUtils.getBeanFactory());
+ public PlusDataPermissionHandler(String mapperPackage) {
+ scanMapperClasses(mapperPackage);
+ }
+
public Expression getSqlSegment(Expression where, String mappedStatementId, boolean isSelect) {
- DataColumn[] dataColumns = findAnnotation(mappedStatementId);
+ DataPermission dataPermission = getDataPermission(mappedStatementId);
LoginUser currentUser = DataPermissionHelper.getVariable("user");
if (ObjectUtil.isNull(currentUser)) {
currentUser = LoginHelper.getLoginUser();
@@ -70,7 +84,7 @@
if (LoginHelper.isSuperAdmin() || LoginHelper.isTenantAdmin()) {
return where;
}
- String dataFilterSql = buildDataFilter(dataColumns, isSelect);
+ String dataFilterSql = buildDataFilter(dataPermission.value(), isSelect);
if (StringUtils.isBlank(dataFilterSql)) {
return where;
}
@@ -144,43 +158,64 @@
return "";
}
- public DataColumn[] findAnnotation(String mappedStatementId) {
- StringBuilder sb = new StringBuilder(mappedStatementId);
- int index = sb.lastIndexOf(".");
- String clazzName = sb.substring(0, index);
- String methodName = sb.substring(index + 1, sb.length());
- Class<?> clazz;
+ /**
+ * 閫氳繃 mapperPackage 璁剧疆鐨勬壂鎻忓寘 鎵弿缂撳瓨鏈夋敞瑙g殑鏂规硶涓庣被
+ */
+ private void scanMapperClasses(String mapperPackage) {
+ PathMatchingResourcePatternResolver resolver = new PathMatchingResourcePatternResolver();
+ CachingMetadataReaderFactory factory = new CachingMetadataReaderFactory();
+ String[] packagePatternArray = StringUtils.splitPreserveAllTokens(mapperPackage, ConfigurableApplicationContext.CONFIG_LOCATION_DELIMITERS);
+ String classpath = ResourcePatternResolver.CLASSPATH_ALL_URL_PREFIX;
try {
- clazz = ClassUtil.loadClass(clazzName);
+ for (String packagePattern : packagePatternArray) {
+ String path = ClassUtils.convertClassNameToResourcePath(packagePattern);
+ Resource[] resources = resolver.getResources(classpath + path + "/*.class");
+ for (Resource resource : resources) {
+ ClassMetadata classMetadata = factory.getMetadataReader(resource).getClassMetadata();
+ Class<?> clazz = Resources.classForName(classMetadata.getClassName());
+ findAnnotation(clazz);
+ }
+ }
} catch (Exception e) {
- return null;
+ log.error("鍒濆鍖栨暟鎹畨鍏ㄧ紦瀛樻椂鍑洪敊:{}", e.getMessage());
}
- List<Method> methods = Arrays.stream(ClassUtil.getDeclaredMethods(clazz))
- .filter(method -> method.getName().equals(methodName)).toList();
+ }
+
+ private void findAnnotation(Class<?> clazz) {
DataPermission dataPermission;
// 鑾峰彇鏂规硶娉ㄨВ
- for (Method method : methods) {
- dataPermission = dataPermissionCacheMap.get(mappedStatementId);
- if (ObjectUtil.isNotNull(dataPermission)) {
- return dataPermission.value();
+ for (Method method : clazz.getMethods()) {
+ if (method.isDefault() || method.isVarArgs()) {
+ continue;
}
+ String mappedStatementId = clazz.getName() + "." + method.getName();
if (AnnotationUtil.hasAnnotation(method, DataPermission.class)) {
dataPermission = AnnotationUtil.getAnnotation(method, DataPermission.class);
dataPermissionCacheMap.put(mappedStatementId, dataPermission);
- return dataPermission.value();
}
- }
- dataPermission = dataPermissionCacheMap.get(clazz.getName());
- if (ObjectUtil.isNotNull(dataPermission)) {
- return dataPermission.value();
}
// 鑾峰彇绫绘敞瑙�
if (AnnotationUtil.hasAnnotation(clazz, DataPermission.class)) {
dataPermission = AnnotationUtil.getAnnotation(clazz, DataPermission.class);
dataPermissionCacheMap.put(clazz.getName(), dataPermission);
- return dataPermission.value();
+ }
+ }
+
+ public DataPermission getDataPermission(String mapperId) {
+ if (dataPermissionCacheMap.containsKey(mapperId)) {
+ return dataPermissionCacheMap.get(mapperId);
+ }
+ String clazzName = mapperId.substring(0, mapperId.lastIndexOf("."));
+ if (dataPermissionCacheMap.containsKey(clazzName)) {
+ return dataPermissionCacheMap.get(clazzName);
}
return null;
}
+ /**
+ * 鏄惁鏃犳晥
+ */
+ public boolean invalid(String mapperId) {
+ return getDataPermission(mapperId) == null;
+ }
}
diff --git a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/interceptor/PlusDataPermissionInterceptor.java b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/interceptor/PlusDataPermissionInterceptor.java
index 0ab0c11..6eed8f7 100644
--- a/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/interceptor/PlusDataPermissionInterceptor.java
+++ b/ruoyi-common/ruoyi-common-mybatis/src/main/java/org/dromara/common/mybatis/interceptor/PlusDataPermissionInterceptor.java
@@ -1,18 +1,16 @@
package org.dromara.common.mybatis.interceptor;
-import cn.hutool.core.collection.ConcurrentHashSet;
-import cn.hutool.core.util.ArrayUtil;
import com.baomidou.mybatisplus.core.plugins.InterceptorIgnoreHelper;
import com.baomidou.mybatisplus.core.toolkit.PluginUtils;
-import com.baomidou.mybatisplus.extension.parser.JsqlParserSupport;
+import com.baomidou.mybatisplus.extension.plugins.handler.MultiDataPermissionHandler;
+import com.baomidou.mybatisplus.extension.plugins.inner.BaseMultiTableInnerInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.InnerInterceptor;
-import org.dromara.common.mybatis.annotation.DataColumn;
-import org.dromara.common.mybatis.handler.PlusDataPermissionHandler;
+import lombok.extern.slf4j.Slf4j;
import net.sf.jsqlparser.expression.Expression;
+import net.sf.jsqlparser.schema.Table;
import net.sf.jsqlparser.statement.delete.Delete;
import net.sf.jsqlparser.statement.select.PlainSelect;
import net.sf.jsqlparser.statement.select.Select;
-import net.sf.jsqlparser.statement.select.SelectBody;
import net.sf.jsqlparser.statement.select.SetOperationList;
import net.sf.jsqlparser.statement.update.Update;
import org.apache.ibatis.executor.Executor;
@@ -22,11 +20,11 @@
import org.apache.ibatis.mapping.SqlCommandType;
import org.apache.ibatis.session.ResultHandler;
import org.apache.ibatis.session.RowBounds;
+import org.dromara.common.mybatis.handler.PlusDataPermissionHandler;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.List;
-import java.util.Set;
/**
* 鏁版嵁鏉冮檺鎷︽埅鍣�
@@ -34,13 +32,14 @@
* @author Lion Li
* @version 3.5.0
*/
-public class PlusDataPermissionInterceptor extends JsqlParserSupport implements InnerInterceptor {
+@Slf4j
+public class PlusDataPermissionInterceptor extends BaseMultiTableInnerInterceptor implements InnerInterceptor {
- private final PlusDataPermissionHandler dataPermissionHandler = new PlusDataPermissionHandler();
- /**
- * 鏃犳晥娉ㄨВ鏂规硶缂撳瓨鐢ㄤ簬蹇�熻繑鍥�
- */
- private final Set<String> invalidCacheSet = new ConcurrentHashSet<>();
+ private final PlusDataPermissionHandler dataPermissionHandler;
+
+ public PlusDataPermissionInterceptor(String mapperPackage) {
+ this.dataPermissionHandler = new PlusDataPermissionHandler(mapperPackage);
+ }
@Override
public void beforeQuery(Executor executor, MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql) throws SQLException {
@@ -49,12 +48,7 @@
return;
}
// 妫�鏌ユ槸鍚︽棤鏁� 鏃犳暟鎹潈闄愭敞瑙�
- if (invalidCacheSet.contains(ms.getId())) {
- return;
- }
- DataColumn[] dataColumns = dataPermissionHandler.findAnnotation(ms.getId());
- if (ArrayUtil.isEmpty(dataColumns)) {
- invalidCacheSet.add(ms.getId());
+ if (dataPermissionHandler.invalid(ms.getId())) {
return;
}
// 瑙f瀽 sql 鍒嗛厤瀵瑰簲鏂规硶
@@ -72,12 +66,7 @@
return;
}
// 妫�鏌ユ槸鍚︽棤鏁� 鏃犳暟鎹潈闄愭敞瑙�
- if (invalidCacheSet.contains(ms.getId())) {
- return;
- }
- DataColumn[] dataColumns = dataPermissionHandler.findAnnotation(ms.getId());
- if (ArrayUtil.isEmpty(dataColumns)) {
- invalidCacheSet.add(ms.getId());
+ if (dataPermissionHandler.invalid(ms.getId())) {
return;
}
PluginUtils.MPBoundSql mpBs = mpSh.mPBoundSql();
@@ -87,11 +76,10 @@
@Override
protected void processSelect(Select select, int index, String sql, Object obj) {
- SelectBody selectBody = select.getSelectBody();
- if (selectBody instanceof PlainSelect plainSelect) {
- this.setWhere(plainSelect, (String) obj);
- } else if (selectBody instanceof SetOperationList setOperationList) {
- List<SelectBody> selectBodyList = setOperationList.getSelects();
+ if (select instanceof PlainSelect) {
+ this.setWhere((PlainSelect) select, (String) obj);
+ } else if (select instanceof SetOperationList setOperationList) {
+ List<Select> selectBodyList = setOperationList.getSelects();
selectBodyList.forEach(s -> this.setWhere((PlainSelect) s, (String) obj));
}
}
@@ -125,5 +113,11 @@
}
}
+ @Override
+ public Expression buildTableExpression(Table table, Expression where, String whereSegment) {
+ // 鍙湁鏂扮増鏁版嵁鏉冮檺澶勭悊鍣ㄦ墠浼氭墽琛屽埌杩欓噷
+ final MultiDataPermissionHandler handler = (MultiDataPermissionHandler) dataPermissionHandler;
+ return handler.getSqlSegment(table, where, whereSegment);
+ }
}
diff --git a/ruoyi-admin/src/main/resources/spy.properties b/ruoyi-common/ruoyi-common-mybatis/src/main/resources/spy.properties
similarity index 80%
rename from ruoyi-admin/src/main/resources/spy.properties
rename to ruoyi-common/ruoyi-common-mybatis/src/main/resources/spy.properties
index abbd893..e9d10f3 100644
--- a/ruoyi-admin/src/main/resources/spy.properties
+++ b/ruoyi-common/ruoyi-common-mybatis/src/main/resources/spy.properties
@@ -6,8 +6,6 @@
appender=com.baomidou.mybatisplus.extension.p6spy.StdoutLogger
# 浣跨敤鏃ュ織绯荤粺璁板綍 sql
#appender=com.p6spy.engine.spy.appender.Slf4JLogger
-# 璁剧疆 p6spy driver 浠g悊
-#deregisterdrivers=true
# 鍙栨秷JDBC URL鍓嶇紑
useprefix=true
# 閰嶇疆璁板綍 Log 渚嬪,鍙幓鎺夌殑缁撴灉闆嗘湁error,info,batch,debug,statement,commit,rollback,result,resultset.
@@ -16,12 +14,6 @@
dateformat=yyyy-MM-dd HH:mm:ss
# SQL璇彞鎵撳嵃鏃堕棿鏍煎紡
databaseDialectTimestampFormat=yyyy-MM-dd HH:mm:ss
-# 瀹為檯椹卞姩鍙涓�
-#driverlist=org.h2.Driver
-# 鏄惁寮�鍚參SQL璁板綍
-outagedetection=true
-# 鎱QL璁板綍鏍囧噯 2 绉�
-outagedetectioninterval=2
# 鏄惁杩囨护 Log
filter=true
# 杩囨护 Log 鏃舵墍鎺掗櫎鐨� sql 鍏抽敭瀛楋紝浠ラ�楀彿鍒嗛殧
diff --git a/ruoyi-common/ruoyi-common-oss/pom.xml b/ruoyi-common/ruoyi-common-oss/pom.xml
index 8e7afff..18d004f 100644
--- a/ruoyi-common/ruoyi-common-oss/pom.xml
+++ b/ruoyi-common/ruoyi-common-oss/pom.xml
@@ -26,10 +26,46 @@
<artifactId>ruoyi-common-redis</artifactId>
</dependency>
+ <!-- AWS SDK for Java 2.x -->
<dependency>
- <groupId>com.amazonaws</groupId>
- <artifactId>aws-java-sdk-s3</artifactId>
+ <groupId>software.amazon.awssdk</groupId>
+ <artifactId>s3</artifactId>
+ <exclusions>
+ <!-- 灏嗗熀浜� Netty 鐨� HTTP 瀹㈡埛绔粠绫昏矾寰勪腑绉婚櫎 -->
+ <exclusion>
+ <groupId>software.amazon.awssdk</groupId>
+ <artifactId>netty-nio-client</artifactId>
+ </exclusion>
+ <!-- 灏嗗熀浜� CRT 鐨� HTTP 瀹㈡埛绔粠绫昏矾寰勪腑绉婚櫎 -->
+ <exclusion>
+ <groupId>software.amazon.awssdk</groupId>
+ <artifactId>aws-crt-client</artifactId>
+ </exclusion>
+ <!-- 灏嗗熀浜� Apache 鐨� HTTP 瀹㈡埛绔粠绫昏矾寰勪腑绉婚櫎 -->
+ <exclusion>
+ <groupId>software.amazon.awssdk</groupId>
+ <artifactId>apache-client</artifactId>
+ </exclusion>
+ <!-- 灏嗛厤缃熀浜� URL 杩炴帴鐨� HTTP 瀹㈡埛绔粠绫昏矾寰勪腑绉婚櫎 -->
+ <exclusion>
+ <groupId>software.amazon.awssdk</groupId>
+ <artifactId>url-connection-client</artifactId>
+ </exclusion>
+ </exclusions>
</dependency>
+
+ <!-- 浣跨敤AWS鍩轰簬 CRT 鐨� S3 瀹㈡埛绔� -->
+ <dependency>
+ <groupId>software.amazon.awssdk.crt</groupId>
+ <artifactId>aws-crt</artifactId>
+ </dependency>
+
+ <!-- 鍩轰簬 AWS CRT 鐨� S3 瀹㈡埛绔殑鎬ц兘澧炲己鐨� S3 浼犺緭绠$悊鍣� -->
+ <dependency>
+ <groupId>software.amazon.awssdk</groupId>
+ <artifactId>s3-transfer-manager</artifactId>
+ </dependency>
+
</dependencies>
</project>
diff --git a/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/core/OssClient.java b/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/core/OssClient.java
index 53e05c9..fcad35b 100644
--- a/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/core/OssClient.java
+++ b/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/core/OssClient.java
@@ -2,73 +2,117 @@
import cn.hutool.core.io.IoUtil;
import cn.hutool.core.util.IdUtil;
-import com.amazonaws.ClientConfiguration;
-import com.amazonaws.HttpMethod;
-import com.amazonaws.Protocol;
-import com.amazonaws.auth.AWSCredentials;
-import com.amazonaws.auth.AWSCredentialsProvider;
-import com.amazonaws.auth.AWSStaticCredentialsProvider;
-import com.amazonaws.auth.BasicAWSCredentials;
-import com.amazonaws.client.builder.AwsClientBuilder;
-import com.amazonaws.services.s3.AmazonS3;
-import com.amazonaws.services.s3.AmazonS3Client;
-import com.amazonaws.services.s3.AmazonS3ClientBuilder;
-import com.amazonaws.services.s3.model.*;
+import org.dromara.common.core.constant.Constants;
import org.dromara.common.core.utils.DateUtils;
import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.core.utils.file.FileUtils;
import org.dromara.common.oss.constant.OssConstant;
import org.dromara.common.oss.entity.UploadResult;
import org.dromara.common.oss.enumd.AccessPolicyType;
import org.dromara.common.oss.enumd.PolicyType;
import org.dromara.common.oss.exception.OssException;
import org.dromara.common.oss.properties.OssProperties;
+import software.amazon.awssdk.auth.credentials.AwsBasicCredentials;
+import software.amazon.awssdk.auth.credentials.StaticCredentialsProvider;
+import software.amazon.awssdk.core.ResponseInputStream;
+import software.amazon.awssdk.core.async.AsyncRequestBody;
+import software.amazon.awssdk.core.async.AsyncResponseTransformer;
+import software.amazon.awssdk.core.async.BlockingInputStreamAsyncRequestBody;
+import software.amazon.awssdk.regions.Region;
+import software.amazon.awssdk.services.s3.S3AsyncClient;
+import software.amazon.awssdk.services.s3.S3Configuration;
+import software.amazon.awssdk.services.s3.model.GetObjectResponse;
+import software.amazon.awssdk.services.s3.model.NoSuchBucketException;
+import software.amazon.awssdk.services.s3.model.S3Exception;
+import software.amazon.awssdk.services.s3.presigner.S3Presigner;
+import software.amazon.awssdk.transfer.s3.S3TransferManager;
+import software.amazon.awssdk.transfer.s3.model.*;
+import software.amazon.awssdk.transfer.s3.progress.LoggingTransferListener;
-import java.io.ByteArrayInputStream;
-import java.io.File;
-import java.io.InputStream;
+import java.io.*;
+import java.net.URI;
import java.net.URL;
-import java.util.Date;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.time.Duration;
/**
* S3 瀛樺偍鍗忚 鎵�鏈夊吋瀹筍3鍗忚鐨勪簯鍘傚晢鍧囨敮鎸�
* 闃块噷浜� 鑵捐浜� 涓冪墰浜� minio
*
- * @author Lion Li
+ * @author AprilWind
*/
public class OssClient {
+ /**
+ * 鏈嶅姟鍟�
+ */
private final String configKey;
+ /**
+ * 閰嶇疆灞炴��
+ */
private final OssProperties properties;
- private final AmazonS3 client;
+ /**
+ * Amazon S3 寮傛瀹㈡埛绔�
+ */
+ private final S3AsyncClient client;
+ /**
+ * 鐢ㄤ簬绠$悊 S3 鏁版嵁浼犺緭鐨勯珮绾у伐鍏�
+ */
+ private final S3TransferManager transferManager;
+
+ /**
+ * AWS S3 棰勭鍚� URL 鐨勭敓鎴愬櫒
+ */
+ private final S3Presigner presigner;
+
+ /**
+ * 鏋勯�犳柟娉�
+ *
+ * @param configKey 閰嶇疆閿�
+ * @param ossProperties Oss閰嶇疆灞炴��
+ */
public OssClient(String configKey, OssProperties ossProperties) {
this.configKey = configKey;
this.properties = ossProperties;
try {
- AwsClientBuilder.EndpointConfiguration endpointConfig =
- new AwsClientBuilder.EndpointConfiguration(properties.getEndpoint(), properties.getRegion());
+ // 鍒涘缓 AWS 璁よ瘉淇℃伅
+ StaticCredentialsProvider credentialsProvider = StaticCredentialsProvider.create(
+ AwsBasicCredentials.create(properties.getAccessKey(), properties.getSecretKey()));
- AWSCredentials credentials = new BasicAWSCredentials(properties.getAccessKey(), properties.getSecretKey());
- AWSCredentialsProvider credentialsProvider = new AWSStaticCredentialsProvider(credentials);
- ClientConfiguration clientConfig = new ClientConfiguration();
- if (OssConstant.IS_HTTPS.equals(properties.getIsHttps())) {
- clientConfig.setProtocol(Protocol.HTTPS);
- } else {
- clientConfig.setProtocol(Protocol.HTTP);
- }
- AmazonS3ClientBuilder build = AmazonS3Client.builder()
- .withEndpointConfiguration(endpointConfig)
- .withClientConfiguration(clientConfig)
- .withCredentials(credentialsProvider)
- .disableChunkedEncoding();
- if (!StringUtils.containsAny(properties.getEndpoint(), OssConstant.CLOUD_SERVICE)) {
- // minio 浣跨敤https闄愬埗浣跨敤鍩熷悕璁块棶 闇�瑕佹閰嶇疆 绔欑偣濉煙鍚�
- build.enablePathStyleAccess();
- }
- this.client = build.build();
+ //MinIO 浣跨敤 HTTPS 闄愬埗浣跨敤鍩熷悕璁块棶锛岀珯鐐瑰~鍩熷悕銆傞渶瑕佸惎鐢ㄨ矾寰勬牱寮忚闂�
+ boolean isStyle = !StringUtils.containsAny(properties.getEndpoint(), OssConstant.CLOUD_SERVICE);
+ //鍒涘缓AWS鍩轰簬 CRT 鐨� S3 瀹㈡埛绔�
+ this.client = S3AsyncClient.crtBuilder()
+ .credentialsProvider(credentialsProvider)
+ .endpointOverride(URI.create(getEndpoint()))
+ .region(of())
+ .targetThroughputInGbps(20.0)
+ .minimumPartSizeInBytes(10 * 1025 * 1024L)
+ .checksumValidationEnabled(false)
+ .forcePathStyle(isStyle)
+ .build();
+
+ //AWS鍩轰簬 CRT 鐨� S3 AsyncClient 瀹炰緥鐢ㄤ綔 S3 浼犺緭绠$悊鍣ㄧ殑搴曞眰瀹㈡埛绔�
+ this.transferManager = S3TransferManager.builder().s3Client(this.client).build();
+
+ // 鍒涘缓 S3 閰嶇疆瀵硅薄
+ S3Configuration config = S3Configuration.builder().chunkedEncodingEnabled(false)
+ .pathStyleAccessEnabled(isStyle).build();
+
+ // 鍒涘缓 棰勭鍚� URL 鐨勭敓鎴愬櫒 瀹炰緥锛岀敤浜庣敓鎴� S3 棰勭鍚� URL
+ this.presigner = S3Presigner.builder()
+ .region(of())
+ .credentialsProvider(credentialsProvider)
+ .endpointOverride(URI.create(getDomain()))
+ .serviceConfiguration(config)
+ .build();
+
+ // 鍒涘缓瀛樺偍妗�
createBucket();
} catch (Exception e) {
if (e instanceof OssException) {
@@ -78,126 +122,189 @@
}
}
+ /**
+ * 鍚屾鍒涘缓瀛樺偍妗�
+ * 濡傛灉瀛樺偍妗朵笉瀛樺湪锛屼細杩涜鍒涘缓锛涘鏋滃瓨鍌ㄦ《瀛樺湪锛屼笉鎵ц浠讳綍鎿嶄綔
+ *
+ * @throws OssException 褰撳垱寤哄瓨鍌ㄦ《鏃跺彂鐢熷紓甯告椂鎶涘嚭
+ */
public void createBucket() {
+ String bucketName = properties.getBucketName();
try {
- String bucketName = properties.getBucketName();
- if (client.doesBucketExistV2(bucketName)) {
- return;
+ // 灏濊瘯鑾峰彇瀛樺偍妗剁殑淇℃伅
+ client.headBucket(
+ x -> x.bucket(bucketName)
+ .build())
+ .join();
+ } catch (Exception ex) {
+ if (ex.getCause() instanceof NoSuchBucketException) {
+ try {
+ // 瀛樺偍妗朵笉瀛樺湪锛屽皾璇曞垱寤哄瓨鍌ㄦ《
+ client.createBucket(
+ x -> x.bucket(bucketName))
+ .join();
+
+ // 璁剧疆瀛樺偍妗剁殑璁块棶绛栫暐锛圔ucket Policy锛�
+ client.putBucketPolicy(
+ x -> x.bucket(bucketName)
+ .policy(getPolicy(bucketName, getAccessPolicy().getPolicyType())))
+ .join();
+ } catch (S3Exception e) {
+ // 瀛樺偍妗跺垱寤烘垨绛栫暐璁剧疆澶辫触
+ throw new OssException("鍒涘缓Bucket澶辫触, 璇锋牳瀵归厤缃俊鎭�:[" + e.getMessage() + "]");
+ }
+ } else {
+ throw new OssException("鍒ゆ柇Bucket鏄惁瀛樺湪澶辫触锛岃鏍稿閰嶇疆淇℃伅:[" + ex.getMessage() + "]");
}
- CreateBucketRequest createBucketRequest = new CreateBucketRequest(bucketName);
- AccessPolicyType accessPolicy = getAccessPolicy();
- createBucketRequest.setCannedAcl(accessPolicy.getAcl());
- client.createBucket(createBucketRequest);
- client.setBucketPolicy(bucketName, getPolicy(bucketName, accessPolicy.getPolicyType()));
- } catch (Exception e) {
- throw new OssException("鍒涘缓Bucket澶辫触, 璇锋牳瀵归厤缃俊鎭�:[" + e.getMessage() + "]");
}
}
- public UploadResult upload(byte[] data, String path, String contentType) {
- return upload(new ByteArrayInputStream(data), path, contentType);
+ /**
+ * 涓婁紶鏂囦欢鍒� Amazon S3锛屽苟杩斿洖涓婁紶缁撴灉
+ *
+ * @param filePath 鏈湴鏂囦欢璺緞
+ * @param key 鍦� Amazon S3 涓殑瀵硅薄閿�
+ * @param md5Digest 鏈湴鏂囦欢鐨� MD5 鍝堝笇鍊硷紙鍙�夛級
+ * @return UploadResult 鍖呭惈涓婁紶鍚庣殑鏂囦欢淇℃伅
+ * @throws OssException 濡傛灉涓婁紶澶辫触锛屾姏鍑鸿嚜瀹氫箟寮傚父
+ */
+ public UploadResult upload(Path filePath, String key, String md5Digest) {
+ try {
+ // 鏋勫缓涓婁紶璇锋眰瀵硅薄
+ FileUpload fileUpload = transferManager.uploadFile(
+ x -> x.putObjectRequest(
+ y -> y.bucket(properties.getBucketName())
+ .key(key)
+ .contentMD5(StringUtils.isNotEmpty(md5Digest) ? md5Digest : null)
+ .build())
+ .addTransferListener(LoggingTransferListener.create())
+ .source(filePath).build());
+
+ // 绛夊緟涓婁紶瀹屾垚骞惰幏鍙栦笂浼犵粨鏋�
+ CompletedFileUpload uploadResult = fileUpload.completionFuture().join();
+ String eTag = uploadResult.response().eTag();
+
+ // 鎻愬彇涓婁紶缁撴灉涓殑 ETag锛屽苟鏋勫缓涓�涓嚜瀹氫箟鐨� UploadResult 瀵硅薄
+ return UploadResult.builder().url(getUrl() + StringUtils.SLASH + key).filename(key).eTag(eTag).build();
+ } catch (Exception e) {
+ // 鎹曡幏寮傚父骞舵姏鍑鸿嚜瀹氫箟寮傚父
+ throw new OssException("涓婁紶鏂囦欢澶辫触锛岃妫�鏌ラ厤缃俊鎭�:[" + e.getMessage() + "]");
+ } finally {
+ // 鏃犺涓婁紶鏄惁鎴愬姛锛屾渶缁堥兘浼氬垹闄や复鏃舵枃浠�
+ FileUtils.del(filePath);
+ }
}
- public UploadResult upload(InputStream inputStream, String path, String contentType) {
+ /**
+ * 涓婁紶 InputStream 鍒� Amazon S3
+ *
+ * @param inputStream 瑕佷笂浼犵殑杈撳叆娴�
+ * @param key 鍦� Amazon S3 涓殑瀵硅薄閿�
+ * @param length 杈撳叆娴佺殑闀垮害
+ * @return UploadResult 鍖呭惈涓婁紶鍚庣殑鏂囦欢淇℃伅
+ * @throws OssException 濡傛灉涓婁紶澶辫触锛屾姏鍑鸿嚜瀹氫箟寮傚父
+ */
+ public UploadResult upload(InputStream inputStream, String key, Long length) {
+ // 濡傛灉杈撳叆娴佷笉鏄� ByteArrayInputStream锛屽垯灏嗗叾璇诲彇涓哄瓧鑺傛暟缁勫啀鍒涘缓 ByteArrayInputStream
if (!(inputStream instanceof ByteArrayInputStream)) {
inputStream = new ByteArrayInputStream(IoUtil.readBytes(inputStream));
}
try {
- ObjectMetadata metadata = new ObjectMetadata();
- metadata.setContentType(contentType);
- metadata.setContentLength(inputStream.available());
- PutObjectRequest putObjectRequest = new PutObjectRequest(properties.getBucketName(), path, inputStream, metadata);
- // 璁剧疆涓婁紶瀵硅薄鐨� Acl 涓哄叕鍏辫
- putObjectRequest.setCannedAcl(getAccessPolicy().getAcl());
- client.putObject(putObjectRequest);
+ // 鍒涘缓寮傛璇锋眰浣擄紙length濡傛灉涓虹┖浼氭姤閿欙級
+ BlockingInputStreamAsyncRequestBody body = AsyncRequestBody.forBlockingInputStream(length);
+
+ // 浣跨敤 transferManager 杩涜涓婁紶
+ Upload upload = transferManager.upload(
+ x -> x.requestBody(body)
+ .putObjectRequest(
+ y -> y.bucket(properties.getBucketName())
+ .key(key)
+ .build())
+ .build());
+
+ // 灏嗚緭鍏ユ祦鍐欏叆璇锋眰浣�
+ body.writeInputStream(inputStream);
+
+ // 绛夊緟鏂囦欢涓婁紶鎿嶄綔瀹屾垚
+ CompletedUpload uploadResult = upload.completionFuture().join();
+ String eTag = uploadResult.response().eTag();
+
+ // 鎻愬彇涓婁紶缁撴灉涓殑 ETag锛屽苟鏋勫缓涓�涓嚜瀹氫箟鐨� UploadResult 瀵硅薄
+ return UploadResult.builder().url(getUrl() + StringUtils.SLASH + key).filename(key).eTag(eTag).build();
} catch (Exception e) {
throw new OssException("涓婁紶鏂囦欢澶辫触锛岃妫�鏌ラ厤缃俊鎭�:[" + e.getMessage() + "]");
}
- return UploadResult.builder().url(getUrl() + "/" + path).filename(path).build();
- }
-
- public UploadResult upload(File file, String path) {
- try {
- PutObjectRequest putObjectRequest = new PutObjectRequest(properties.getBucketName(), path, file);
- // 璁剧疆涓婁紶瀵硅薄鐨� Acl 涓哄叕鍏辫
- putObjectRequest.setCannedAcl(getAccessPolicy().getAcl());
- client.putObject(putObjectRequest);
- } catch (Exception e) {
- throw new OssException("涓婁紶鏂囦欢澶辫触锛岃妫�鏌ラ厤缃俊鎭�:[" + e.getMessage() + "]");
- }
- return UploadResult.builder().url(getUrl() + "/" + path).filename(path).build();
- }
-
- public void delete(String path) {
- path = path.replace(getUrl() + "/", "");
- try {
- client.deleteObject(properties.getBucketName(), path);
- } catch (Exception e) {
- throw new OssException("鍒犻櫎鏂囦欢澶辫触锛岃妫�鏌ラ厤缃俊鎭�:[" + e.getMessage() + "]");
- }
- }
-
- public UploadResult uploadSuffix(byte[] data, String suffix, String contentType) {
- return upload(data, getPath(properties.getPrefix(), suffix), contentType);
- }
-
- public UploadResult uploadSuffix(InputStream inputStream, String suffix, String contentType) {
- return upload(inputStream, getPath(properties.getPrefix(), suffix), contentType);
- }
-
- public UploadResult uploadSuffix(File file, String suffix) {
- return upload(file, getPath(properties.getPrefix(), suffix));
}
/**
- * 鑾峰彇鏂囦欢鍏冩暟鎹�
+ * 涓嬭浇鏂囦欢浠� Amazon S3 鍒颁复鏃剁洰褰�
*
- * @param path 瀹屾暣鏂囦欢璺緞
+ * @param path 鏂囦欢鍦� Amazon S3 涓殑瀵硅薄閿�
+ * @return 涓嬭浇鍚庣殑鏂囦欢鍦ㄦ湰鍦扮殑涓存椂璺緞
+ * @throws OssException 濡傛灉涓嬭浇澶辫触锛屾姏鍑鸿嚜瀹氫箟寮傚父
*/
- public ObjectMetadata getObjectMetadata(String path) {
- path = path.replace(getUrl() + "/", "");
- S3Object object = client.getObject(properties.getBucketName(), path);
- return object.getObjectMetadata();
+ public Path fileDownload(String path) {
+ // 鏋勫缓涓存椂鏂囦欢
+ Path tempFilePath = FileUtils.createTempFile().toPath();
+ // 浣跨敤 S3TransferManager 涓嬭浇鏂囦欢
+ FileDownload downloadFile = transferManager.downloadFile(
+ x -> x.getObjectRequest(
+ y -> y.bucket(properties.getBucketName())
+ .key(removeBaseUrl(path))
+ .build())
+ .addTransferListener(LoggingTransferListener.create())
+ .destination(tempFilePath)
+ .build());
+ // 绛夊緟鏂囦欢涓嬭浇鎿嶄綔瀹屾垚
+ downloadFile.completionFuture().join();
+ return tempFilePath;
}
- public InputStream getObjectContent(String path) {
- path = path.replace(getUrl() + "/", "");
- S3Object object = client.getObject(properties.getBucketName(), path);
- return object.getObjectContent();
- }
-
- public String getUrl() {
- String domain = properties.getDomain();
- String endpoint = properties.getEndpoint();
- String header = OssConstant.IS_HTTPS.equals(properties.getIsHttps()) ? "https://" : "http://";
- // 浜戞湇鍔″晢鐩存帴杩斿洖
- if (StringUtils.containsAny(endpoint, OssConstant.CLOUD_SERVICE)) {
- if (StringUtils.isNotBlank(domain)) {
- return header + domain;
+ /**
+ * 涓嬭浇鏂囦欢浠� Amazon S3 鍒� 杈撳嚭娴�
+ *
+ * @param key 鏂囦欢鍦� Amazon S3 涓殑瀵硅薄閿�
+ * @param out 杈撳嚭娴�
+ * @return 杈撳嚭娴佷腑鍐欏叆鐨勫瓧鑺傛暟锛堥暱搴︼級
+ * @throws OssException 濡傛灉涓嬭浇澶辫触锛屾姏鍑鸿嚜瀹氫箟寮傚父
+ */
+ public long download(String key, OutputStream out) {
+ try {
+ // 鏋勫缓涓嬭浇璇锋眰
+ DownloadRequest<ResponseInputStream<GetObjectResponse>> downloadRequest = DownloadRequest.builder()
+ // 鏂囦欢瀵硅薄
+ .getObjectRequest(y -> y.bucket(properties.getBucketName())
+ .key(key)
+ .build())
+ .addTransferListener(LoggingTransferListener.create())
+ // 浣跨敤璁㈤槄杞崲鍣�
+ .responseTransformer(AsyncResponseTransformer.toBlockingInputStream())
+ .build();
+ // 浣跨敤 S3TransferManager 涓嬭浇鏂囦欢
+ Download<ResponseInputStream<GetObjectResponse>> responseFuture = transferManager.download(downloadRequest);
+ // 杈撳嚭鍒版祦涓�
+ try (ResponseInputStream<GetObjectResponse> responseStream = responseFuture.completionFuture().join().result()) { // auto-closeable stream
+ return responseStream.transferTo(out); // 闃诲璋冪敤绾跨▼ blocks the calling thread
}
- return header + properties.getBucketName() + "." + endpoint;
+ } catch (Exception e) {
+ throw new OssException("鏂囦欢涓嬭浇澶辫触锛岄敊璇俊鎭�:[" + e.getMessage() + "]");
}
- // minio 鍗曠嫭澶勭悊
- if (StringUtils.isNotBlank(domain)) {
- return header + domain + "/" + properties.getBucketName();
- }
- return header + endpoint + "/" + properties.getBucketName();
}
- public String getPath(String prefix, String suffix) {
- // 鐢熸垚uuid
- String uuid = IdUtil.fastSimpleUUID();
- // 鏂囦欢璺緞
- String path = DateUtils.datePath() + "/" + uuid;
- if (StringUtils.isNotBlank(prefix)) {
- path = prefix + "/" + path;
+ /**
+ * 鍒犻櫎浜戝瓨鍌ㄦ湇鍔′腑鎸囧畾璺緞涓嬫枃浠�
+ *
+ * @param path 鎸囧畾璺緞
+ */
+ public void delete(String path) {
+ try {
+ client.deleteObject(
+ x -> x.bucket(properties.getBucketName())
+ .key(removeBaseUrl(path))
+ .build());
+ } catch (Exception e) {
+ throw new OssException("鍒犻櫎鏂囦欢澶辫触锛岃妫�鏌ラ厤缃俊鎭�:[" + e.getMessage() + "]");
}
- return path + suffix;
- }
-
-
- public String getConfigKey() {
- return configKey;
}
/**
@@ -207,12 +314,187 @@
* @param second 鎺堟潈鏃堕棿
*/
public String getPrivateUrl(String objectKey, Integer second) {
- GeneratePresignedUrlRequest generatePresignedUrlRequest =
- new GeneratePresignedUrlRequest(properties.getBucketName(), objectKey)
- .withMethod(HttpMethod.GET)
- .withExpiration(new Date(System.currentTimeMillis() + 1000L * second));
- URL url = client.generatePresignedUrl(generatePresignedUrlRequest);
+ // 浣跨敤 AWS S3 棰勭鍚� URL 鐨勭敓鎴愬櫒 鑾峰彇瀵硅薄鐨勯绛惧悕 URL
+ URL url = presigner.presignGetObject(
+ x -> x.signatureDuration(Duration.ofSeconds(second))
+ .getObjectRequest(
+ y -> y.bucket(properties.getBucketName())
+ .key(objectKey)
+ .build())
+ .build())
+ .url();
return url.toString();
+ }
+
+ /**
+ * 涓婁紶 byte[] 鏁版嵁鍒� Amazon S3锛屼娇鐢ㄦ寚瀹氱殑鍚庣紑鏋勯�犲璞¢敭銆�
+ *
+ * @param data 瑕佷笂浼犵殑 byte[] 鏁版嵁
+ * @param suffix 瀵硅薄閿殑鍚庣紑
+ * @return UploadResult 鍖呭惈涓婁紶鍚庣殑鏂囦欢淇℃伅
+ * @throws OssException 濡傛灉涓婁紶澶辫触锛屾姏鍑鸿嚜瀹氫箟寮傚父
+ */
+ public UploadResult uploadSuffix(byte[] data, String suffix) {
+ return upload(new ByteArrayInputStream(data), getPath(properties.getPrefix(), suffix), Long.valueOf(data.length));
+ }
+
+ /**
+ * 涓婁紶 InputStream 鍒� Amazon S3锛屼娇鐢ㄦ寚瀹氱殑鍚庣紑鏋勯�犲璞¢敭銆�
+ *
+ * @param inputStream 瑕佷笂浼犵殑杈撳叆娴�
+ * @param suffix 瀵硅薄閿殑鍚庣紑
+ * @param length 杈撳叆娴佺殑闀垮害
+ * @return UploadResult 鍖呭惈涓婁紶鍚庣殑鏂囦欢淇℃伅
+ * @throws OssException 濡傛灉涓婁紶澶辫触锛屾姏鍑鸿嚜瀹氫箟寮傚父
+ */
+ public UploadResult uploadSuffix(InputStream inputStream, String suffix, Long length) {
+ return upload(inputStream, getPath(properties.getPrefix(), suffix), length);
+ }
+
+ /**
+ * 涓婁紶鏂囦欢鍒� Amazon S3锛屼娇鐢ㄦ寚瀹氱殑鍚庣紑鏋勯�犲璞¢敭
+ *
+ * @param file 瑕佷笂浼犵殑鏂囦欢
+ * @param suffix 瀵硅薄閿殑鍚庣紑
+ * @return UploadResult 鍖呭惈涓婁紶鍚庣殑鏂囦欢淇℃伅
+ * @throws OssException 濡傛灉涓婁紶澶辫触锛屾姏鍑鸿嚜瀹氫箟寮傚父
+ */
+ public UploadResult uploadSuffix(File file, String suffix) {
+ return upload(file.toPath(), getPath(properties.getPrefix(), suffix), null);
+ }
+
+ /**
+ * 鑾峰彇鏂囦欢杈撳叆娴�
+ *
+ * @param path 瀹屾暣鏂囦欢璺緞
+ * @return 杈撳叆娴�
+ */
+ public InputStream getObjectContent(String path) throws IOException {
+ // 涓嬭浇鏂囦欢鍒颁复鏃剁洰褰�
+ Path tempFilePath = fileDownload(path);
+ // 鍒涘缓杈撳叆娴�
+ InputStream inputStream = Files.newInputStream(tempFilePath);
+ // 鍒犻櫎涓存椂鏂囦欢
+ FileUtils.del(tempFilePath);
+ // 杩斿洖瀵硅薄鍐呭鐨勮緭鍏ユ祦
+ return inputStream;
+ }
+
+ /**
+ * 鑾峰彇 S3 瀹㈡埛绔殑缁堢鐐� URL
+ *
+ * @return 缁堢鐐� URL
+ */
+ public String getEndpoint() {
+ // 鏍规嵁閰嶇疆鏂囦欢涓殑鏄惁浣跨敤 HTTPS锛岃缃崗璁ご閮�
+ String header = getIsHttps();
+ // 鎷兼帴鍗忚澶撮儴鍜岀粓绔偣锛屽緱鍒板畬鏁寸殑缁堢鐐� URL
+ return header + properties.getEndpoint();
+ }
+
+ /**
+ * 鑾峰彇 S3 瀹㈡埛绔殑缁堢鐐� URL锛堣嚜瀹氫箟鍩熷悕锛�
+ *
+ * @return 缁堢鐐� URL
+ */
+ public String getDomain() {
+ // 浠庨厤缃腑鑾峰彇鍩熷悕銆佺粓绔偣銆佹槸鍚︿娇鐢� HTTPS 绛変俊鎭�
+ String domain = properties.getDomain();
+ String endpoint = properties.getEndpoint();
+ String header = getIsHttps();
+
+ // 濡傛灉鏄簯鏈嶅姟鍟嗭紝鐩存帴杩斿洖鍩熷悕鎴栫粓绔偣
+ if (StringUtils.containsAny(endpoint, OssConstant.CLOUD_SERVICE)) {
+ return StringUtils.isNotEmpty(domain) ? header + domain : header + endpoint;
+ }
+
+ // 濡傛灉鏄� MinIO锛屽鐞嗗煙鍚嶅苟杩斿洖
+ if (StringUtils.isNotEmpty(domain)) {
+ return domain.startsWith(Constants.HTTPS) || domain.startsWith(Constants.HTTP) ? domain : header + domain;
+ }
+
+ // 杩斿洖缁堢鐐�
+ return header + endpoint;
+ }
+
+ /**
+ * 鏍规嵁浼犲叆鐨� region 鍙傛暟杩斿洖鐩稿簲鐨� AWS 鍖哄煙
+ * 濡傛灉 region 鍙傛暟闈炵┖锛屼娇鐢� Region.of 鏂规硶鍒涘缓骞惰繑鍥炲搴旂殑 AWS 鍖哄煙瀵硅薄
+ * 濡傛灉 region 鍙傛暟涓虹┖锛岃繑鍥炰竴涓粯璁ょ殑 AWS 鍖哄煙锛堜緥濡傦紝us-east-1锛夛紝浣滀负骞挎硾鏀寔鐨勫尯鍩�
+ *
+ * @return 瀵瑰簲鐨� AWS 鍖哄煙瀵硅薄锛屾垨鑰呴粯璁ょ殑骞挎硾鏀寔鐨勫尯鍩燂紙us-east-1锛�
+ */
+ public Region of() {
+ //AWS 鍖哄煙瀛楃涓�
+ String region = properties.getRegion();
+ // 濡傛灉 region 鍙傛暟闈炵┖锛屼娇鐢� Region.of 鏂规硶鍒涘缓瀵瑰簲鐨� AWS 鍖哄煙瀵硅薄锛屽惁鍒欒繑鍥為粯璁ゅ尯鍩�
+ return StringUtils.isNotEmpty(region) ? Region.of(region) : Region.US_EAST_1;
+ }
+
+ /**
+ * 鑾峰彇浜戝瓨鍌ㄦ湇鍔$殑URL
+ *
+ * @return 鏂囦欢璺緞
+ */
+ public String getUrl() {
+ String domain = properties.getDomain();
+ String endpoint = properties.getEndpoint();
+ String header = getIsHttps();
+ // 浜戞湇鍔″晢鐩存帴杩斿洖
+ if (StringUtils.containsAny(endpoint, OssConstant.CLOUD_SERVICE)) {
+ return header + (StringUtils.isNotEmpty(domain) ? domain : properties.getBucketName() + "." + endpoint);
+ }
+ // MinIO 鍗曠嫭澶勭悊
+ if (StringUtils.isNotEmpty(domain)) {
+ // 濡傛灉 domain 浠� "https://" 鎴� "http://" 寮�澶�
+ return (domain.startsWith(Constants.HTTPS) || domain.startsWith(Constants.HTTP)) ?
+ domain + StringUtils.SLASH + properties.getBucketName() : header + domain + StringUtils.SLASH + properties.getBucketName();
+ }
+ return header + endpoint + StringUtils.SLASH + properties.getBucketName();
+ }
+
+ /**
+ * 鐢熸垚涓�涓鍚堢壒瀹氳鍒欑殑銆佸敮涓�鐨勬枃浠惰矾寰勩�傞�氳繃浣跨敤鏃ユ湡銆乁UID銆佸墠缂�鍜屽悗缂�绛夊厓绱犵殑缁勫悎锛岀‘淇濅簡鏂囦欢璺緞鐨勭嫭涓�鏃犱簩鎬�
+ *
+ * @param prefix 鍓嶇紑
+ * @param suffix 鍚庣紑
+ * @return 鏂囦欢璺緞
+ */
+ public String getPath(String prefix, String suffix) {
+ // 鐢熸垚uuid
+ String uuid = IdUtil.fastSimpleUUID();
+ // 鐢熸垚鏃ユ湡璺緞
+ String datePath = DateUtils.datePath();
+ // 鎷兼帴璺緞
+ String path = StringUtils.isNotEmpty(prefix) ?
+ prefix + StringUtils.SLASH + datePath + StringUtils.SLASH + uuid : datePath + StringUtils.SLASH + uuid;
+ return path + suffix;
+ }
+
+ /**
+ * 绉婚櫎璺緞涓殑鍩虹URL閮ㄥ垎锛屽緱鍒扮浉瀵硅矾寰�
+ *
+ * @param path 瀹屾暣鐨勮矾寰勶紝鍖呮嫭鍩虹URL鍜岀浉瀵硅矾寰�
+ * @return 鍘婚櫎鍩虹URL鍚庣殑鐩稿璺緞
+ */
+ public String removeBaseUrl(String path) {
+ return path.replace(getUrl() + StringUtils.SLASH, "");
+ }
+
+ /**
+ * 鏈嶅姟鍟�
+ */
+ public String getConfigKey() {
+ return configKey;
+ }
+
+ /**
+ * 鑾峰彇鏄惁浣跨敤 HTTPS 鐨勯厤缃紝骞惰繑鍥炵浉搴旂殑鍗忚澶撮儴銆�
+ *
+ * @return 鍗忚澶撮儴锛屾牴鎹槸鍚︿娇鐢� HTTPS 杩斿洖 "https://" 鎴� "http://"
+ */
+ public String getIsHttps() {
+ return OssConstant.IS_HTTPS.equals(properties.getIsHttps()) ? Constants.HTTPS : Constants.HTTP;
}
/**
@@ -231,32 +513,77 @@
return AccessPolicyType.getByType(properties.getAccessPolicy());
}
+ /**
+ * 鐢熸垚 AWS S3 瀛樺偍妗惰闂瓥鐣�
+ *
+ * @param bucketName 瀛樺偍妗�
+ * @param policyType 妗剁瓥鐣ョ被鍨�
+ * @return 绗﹀悎 AWS S3 瀛樺偍妗惰闂瓥鐣ユ牸寮忕殑瀛楃涓�
+ */
private static String getPolicy(String bucketName, PolicyType policyType) {
- StringBuilder builder = new StringBuilder();
- builder.append("{\n\"Statement\": [\n{\n\"Action\": [\n");
- builder.append(switch (policyType) {
- case WRITE -> "\"s3:GetBucketLocation\",\n\"s3:ListBucketMultipartUploads\"\n";
- case READ_WRITE -> "\"s3:GetBucketLocation\",\n\"s3:ListBucket\",\n\"s3:ListBucketMultipartUploads\"\n";
- default -> "\"s3:GetBucketLocation\"\n";
- });
- builder.append("],\n\"Effect\": \"Allow\",\n\"Principal\": \"*\",\n\"Resource\": \"arn:aws:s3:::");
- builder.append(bucketName);
- builder.append("\"\n},\n");
- if (policyType == PolicyType.READ) {
- builder.append("{\n\"Action\": [\n\"s3:ListBucket\"\n],\n\"Effect\": \"Deny\",\n\"Principal\": \"*\",\n\"Resource\": \"arn:aws:s3:::");
- builder.append(bucketName);
- builder.append("\"\n},\n");
- }
- builder.append("{\n\"Action\": ");
- builder.append(switch (policyType) {
- case WRITE -> "[\n\"s3:AbortMultipartUpload\",\n\"s3:DeleteObject\",\n\"s3:ListMultipartUploadParts\",\n\"s3:PutObject\"\n],\n";
- case READ_WRITE -> "[\n\"s3:AbortMultipartUpload\",\n\"s3:DeleteObject\",\n\"s3:GetObject\",\n\"s3:ListMultipartUploadParts\",\n\"s3:PutObject\"\n],\n";
- default -> "\"s3:GetObject\",\n";
- });
- builder.append("\"Effect\": \"Allow\",\n\"Principal\": \"*\",\n\"Resource\": \"arn:aws:s3:::");
- builder.append(bucketName);
- builder.append("/*\"\n}\n],\n\"Version\": \"2012-10-17\"\n}\n");
- return builder.toString();
+ String policy = switch (policyType) {
+ case WRITE -> """
+ {
+ "Version": "2012-10-17",
+ "Statement": []
+ }
+ """;
+ case READ_WRITE -> """
+ {
+ "Version": "2012-10-17",
+ "Statement": [
+ {
+ "Effect": "Allow",
+ "Principal": "*",
+ "Action": [
+ "s3:GetBucketLocation",
+ "s3:ListBucket",
+ "s3:ListBucketMultipartUploads"
+ ],
+ "Resource": "arn:aws:s3:::bucketName"
+ },
+ {
+ "Effect": "Allow",
+ "Principal": "*",
+ "Action": [
+ "s3:AbortMultipartUpload",
+ "s3:DeleteObject",
+ "s3:GetObject",
+ "s3:ListMultipartUploadParts",
+ "s3:PutObject"
+ ],
+ "Resource": "arn:aws:s3:::bucketName/*"
+ }
+ ]
+ }
+ """;
+ case READ -> """
+ {
+ "Version": "2012-10-17",
+ "Statement": [
+ {
+ "Effect": "Allow",
+ "Principal": "*",
+ "Action": ["s3:GetBucketLocation"],
+ "Resource": "arn:aws:s3:::bucketName"
+ },
+ {
+ "Effect": "Deny",
+ "Principal": "*",
+ "Action": ["s3:ListBucket"],
+ "Resource": "arn:aws:s3:::bucketName"
+ },
+ {
+ "Effect": "Allow",
+ "Principal": "*",
+ "Action": "s3:GetObject",
+ "Resource": "arn:aws:s3:::bucketName/*"
+ }
+ ]
+ }
+ """;
+ };
+ return policy.replaceAll("bucketName", bucketName);
}
}
diff --git a/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/entity/UploadResult.java b/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/entity/UploadResult.java
index a6f57e5..81a18e6 100644
--- a/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/entity/UploadResult.java
+++ b/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/entity/UploadResult.java
@@ -21,4 +21,10 @@
* 鏂囦欢鍚�
*/
private String filename;
+
+ /**
+ * 宸蹭笂浼犲璞$殑瀹炰綋鏍囪锛堢敤鏉ユ牎楠屾枃浠讹級
+ */
+ private String eTag;
+
}
diff --git a/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/enumd/AccessPolicyType.java b/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/enumd/AccessPolicyType.java
index 9074d72..6d39133 100644
--- a/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/enumd/AccessPolicyType.java
+++ b/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/enumd/AccessPolicyType.java
@@ -1,8 +1,9 @@
package org.dromara.common.oss.enumd;
-import com.amazonaws.services.s3.model.CannedAccessControlList;
import lombok.AllArgsConstructor;
import lombok.Getter;
+import software.amazon.awssdk.services.s3.model.BucketCannedACL;
+import software.amazon.awssdk.services.s3.model.ObjectCannedACL;
/**
* 妗惰闂瓥鐣ラ厤缃�
@@ -16,27 +17,32 @@
/**
* private
*/
- PRIVATE("0", CannedAccessControlList.Private, PolicyType.WRITE),
+ PRIVATE("0", BucketCannedACL.PRIVATE, ObjectCannedACL.PRIVATE, PolicyType.WRITE),
/**
* public
*/
- PUBLIC("1", CannedAccessControlList.PublicRead, PolicyType.READ),
+ PUBLIC("1", BucketCannedACL.PUBLIC_READ_WRITE, ObjectCannedACL.PUBLIC_READ_WRITE, PolicyType.READ_WRITE),
/**
* custom
*/
- CUSTOM("2",CannedAccessControlList.PublicRead, PolicyType.READ);
+ CUSTOM("2", BucketCannedACL.PUBLIC_READ, ObjectCannedACL.PUBLIC_READ, PolicyType.READ);
/**
- * 妗� 鏉冮檺绫诲瀷
+ * 妗� 鏉冮檺绫诲瀷锛堟暟鎹簱鍊硷級
*/
private final String type;
/**
+ * 妗� 鏉冮檺绫诲瀷
+ */
+ private final BucketCannedACL bucketCannedACL;
+
+ /**
* 鏂囦欢瀵硅薄 鏉冮檺绫诲瀷
*/
- private final CannedAccessControlList acl;
+ private final ObjectCannedACL objectCannedACL;
/**
* 妗剁瓥鐣ョ被鍨�
diff --git a/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/factory/OssFactory.java b/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/factory/OssFactory.java
index 763b090..d70270a 100644
--- a/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/factory/OssFactory.java
+++ b/ruoyi-common/ruoyi-common-oss/src/main/java/org/dromara/common/oss/factory/OssFactory.java
@@ -1,5 +1,6 @@
package org.dromara.common.oss.factory;
+import lombok.extern.slf4j.Slf4j;
import org.dromara.common.core.constant.CacheNames;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.json.utils.JsonUtils;
@@ -9,10 +10,10 @@
import org.dromara.common.oss.properties.OssProperties;
import org.dromara.common.redis.utils.CacheUtils;
import org.dromara.common.redis.utils.RedisUtils;
-import lombok.extern.slf4j.Slf4j;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.locks.ReentrantLock;
/**
* 鏂囦欢涓婁紶Factory
@@ -23,6 +24,7 @@
public class OssFactory {
private static final Map<String, OssClient> CLIENT_CACHE = new ConcurrentHashMap<>();
+ private static final ReentrantLock LOCK = new ReentrantLock();
/**
* 鑾峰彇榛樿瀹炰緥
@@ -39,7 +41,7 @@
/**
* 鏍规嵁绫诲瀷鑾峰彇瀹炰緥
*/
- public static synchronized OssClient instance(String configKey) {
+ public static OssClient instance(String configKey) {
String json = CacheUtils.get(CacheNames.SYS_OSS_CONFIG, configKey);
if (json == null) {
throw new OssException("绯荤粺寮傚父, '" + configKey + "'閰嶇疆淇℃伅涓嶅瓨鍦�!");
@@ -48,16 +50,19 @@
// 浣跨敤绉熸埛鏍囪瘑閬垮厤澶氫釜绉熸埛鐩稿悓key瀹炰緥瑕嗙洊
String key = properties.getTenantId() + ":" + configKey;
OssClient client = CLIENT_CACHE.get(key);
- if (client == null) {
- CLIENT_CACHE.put(key, new OssClient(configKey, properties));
- log.info("鍒涘缓OSS瀹炰緥 key => {}", configKey);
- return CLIENT_CACHE.get(key);
- }
- // 閰嶇疆涓嶇浉鍚屽垯閲嶆柊鏋勫缓
- if (!client.checkPropertiesSame(properties)) {
- CLIENT_CACHE.put(key, new OssClient(configKey, properties));
- log.info("閲嶈浇OSS瀹炰緥 key => {}", configKey);
- return CLIENT_CACHE.get(key);
+ // 瀹㈡埛绔笉瀛樺湪鎴栭厤缃笉鐩稿悓鍒欓噸鏂版瀯寤�
+ if (client == null || !client.checkPropertiesSame(properties)) {
+ LOCK.lock();
+ try {
+ client = CLIENT_CACHE.get(key);
+ if (client == null || !client.checkPropertiesSame(properties)) {
+ CLIENT_CACHE.put(key, new OssClient(configKey, properties));
+ log.info("鍒涘缓OSS瀹炰緥 key => {}", configKey);
+ return CLIENT_CACHE.get(key);
+ }
+ } finally {
+ LOCK.unlock();
+ }
}
return client;
}
diff --git a/ruoyi-common/ruoyi-common-ratelimiter/src/main/java/org/dromara/common/ratelimiter/aspectj/RateLimiterAspect.java b/ruoyi-common/ruoyi-common-ratelimiter/src/main/java/org/dromara/common/ratelimiter/aspectj/RateLimiterAspect.java
index 8f3a5ca..02735b0 100644
--- a/ruoyi-common/ruoyi-common-ratelimiter/src/main/java/org/dromara/common/ratelimiter/aspectj/RateLimiterAspect.java
+++ b/ruoyi-common/ruoyi-common-ratelimiter/src/main/java/org/dromara/common/ratelimiter/aspectj/RateLimiterAspect.java
@@ -1,29 +1,29 @@
package org.dromara.common.ratelimiter.aspectj;
-import cn.hutool.core.util.ArrayUtil;
-import org.dromara.common.core.constant.GlobalConstants;
-import org.dromara.common.core.exception.ServiceException;
-import org.dromara.common.core.utils.MessageUtils;
-import org.dromara.common.core.utils.ServletUtils;
-import org.dromara.common.core.utils.StringUtils;
-import org.dromara.common.ratelimiter.annotation.RateLimiter;
-import org.dromara.common.ratelimiter.enums.LimitType;
-import org.dromara.common.redis.utils.RedisUtils;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.reflect.MethodSignature;
+import org.dromara.common.core.constant.GlobalConstants;
+import org.dromara.common.core.exception.ServiceException;
+import org.dromara.common.core.utils.MessageUtils;
+import org.dromara.common.core.utils.ServletUtils;
+import org.dromara.common.core.utils.SpringUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.ratelimiter.annotation.RateLimiter;
+import org.dromara.common.ratelimiter.enums.LimitType;
+import org.dromara.common.redis.utils.RedisUtils;
import org.redisson.api.RateType;
+import org.springframework.context.expression.BeanFactoryResolver;
+import org.springframework.context.expression.MethodBasedEvaluationContext;
import org.springframework.core.DefaultParameterNameDiscoverer;
import org.springframework.core.ParameterNameDiscoverer;
-import org.springframework.expression.EvaluationContext;
import org.springframework.expression.Expression;
import org.springframework.expression.ExpressionParser;
import org.springframework.expression.ParserContext;
import org.springframework.expression.common.TemplateParserContext;
import org.springframework.expression.spel.standard.SpelExpressionParser;
-import org.springframework.expression.spel.support.StandardEvaluationContext;
import java.lang.reflect.Method;
@@ -45,20 +45,17 @@
*/
private final ParserContext parserContext = new TemplateParserContext();
/**
- * 瀹氫箟spel涓婁笅鏂囧璞¤繘琛岃В鏋�
- */
- private final EvaluationContext context = new StandardEvaluationContext();
- /**
* 鏂规硶鍙傛暟瑙f瀽鍣�
*/
private final ParameterNameDiscoverer pnd = new DefaultParameterNameDiscoverer();
+
@Before("@annotation(rateLimiter)")
- public void doBefore(JoinPoint point, RateLimiter rateLimiter) throws Throwable {
+ public void doBefore(JoinPoint point, RateLimiter rateLimiter) {
int time = rateLimiter.time();
int count = rateLimiter.count();
- String combineKey = getCombineKey(rateLimiter, point);
try {
+ String combineKey = getCombineKey(rateLimiter, point);
RateType rateType = RateType.OVERALL;
if (rateLimiter.limitType() == LimitType.CLUSTER) {
rateType = RateType.PER_CLIENT;
@@ -76,42 +73,29 @@
if (e instanceof ServiceException) {
throw e;
} else {
- throw new RuntimeException("鏈嶅姟鍣ㄩ檺娴佸紓甯革紝璇风◢鍊欏啀璇�");
+ throw new RuntimeException("鏈嶅姟鍣ㄩ檺娴佸紓甯革紝璇风◢鍊欏啀璇�", e);
}
}
}
- public String getCombineKey(RateLimiter rateLimiter, JoinPoint point) {
+ private String getCombineKey(RateLimiter rateLimiter, JoinPoint point) {
String key = rateLimiter.key();
- // 鑾峰彇鏂规硶(閫氳繃鏂规硶绛惧悕鏉ヨ幏鍙�)
- MethodSignature signature = (MethodSignature) point.getSignature();
- Method method = signature.getMethod();
- Class<?> targetClass = method.getDeclaringClass();
- // 鍒ゆ柇鏄惁鏄痵pel鏍煎紡
- if (StringUtils.containsAny(key, "#")) {
- // 鑾峰彇鍙傛暟鍊�
+ if (StringUtils.isNotBlank(key)) {
+ MethodSignature signature = (MethodSignature) point.getSignature();
+ Method targetMethod = signature.getMethod();
Object[] args = point.getArgs();
- // 鑾峰彇鏂规硶涓婂弬鏁扮殑鍚嶇О
- String[] parameterNames = pnd.getParameterNames(method);
- if (ArrayUtil.isEmpty(parameterNames)) {
- throw new ServiceException("闄愭祦key瑙f瀽寮傚父!璇疯仈绯荤鐞嗗憳!");
+ //noinspection DataFlowIssue
+ MethodBasedEvaluationContext context =
+ new MethodBasedEvaluationContext(null, targetMethod, args, pnd);
+ context.setBeanResolver(new BeanFactoryResolver(SpringUtils.getBeanFactory()));
+ Expression expression;
+ if (StringUtils.startsWith(key, parserContext.getExpressionPrefix())
+ && StringUtils.endsWith(key, parserContext.getExpressionSuffix())) {
+ expression = parser.parseExpression(key, parserContext);
+ } else {
+ expression = parser.parseExpression(key);
}
- for (int i = 0; i < parameterNames.length; i++) {
- context.setVariable(parameterNames[i], args[i]);
- }
- // 瑙f瀽杩斿洖缁檏ey
- try {
- Expression expression;
- if (StringUtils.startsWith(key, parserContext.getExpressionPrefix())
- && StringUtils.endsWith(key, parserContext.getExpressionSuffix())) {
- expression = parser.parseExpression(key, parserContext);
- } else {
- expression = parser.parseExpression(key);
- }
- key = expression.getValue(context, String.class) + ":";
- } catch (Exception e) {
- throw new ServiceException("闄愭祦key瑙f瀽寮傚父!璇疯仈绯荤鐞嗗憳!");
- }
+ key = expression.getValue(context, String.class);
}
StringBuilder stringBuffer = new StringBuilder(GlobalConstants.RATE_LIMIT_KEY);
stringBuffer.append(ServletUtils.getRequest().getRequestURI()).append(":");
diff --git a/ruoyi-common/ruoyi-common-ratelimiter/src/main/resources/spel-extension.json b/ruoyi-common/ruoyi-common-ratelimiter/src/main/resources/spel-extension.json
new file mode 100644
index 0000000..b16432b
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-ratelimiter/src/main/resources/spel-extension.json
@@ -0,0 +1,7 @@
+{
+ "org.dromara.common.ratelimiter.annotation.RateLimiter@key": {
+ "method": {
+ "parameters": true
+ }
+ }
+}
diff --git a/ruoyi-common/ruoyi-common-redis/pom.xml b/ruoyi-common/ruoyi-common-redis/pom.xml
index 5e5c277..f56f8aa 100644
--- a/ruoyi-common/ruoyi-common-redis/pom.xml
+++ b/ruoyi-common/ruoyi-common-redis/pom.xml
@@ -32,6 +32,16 @@
<groupId>com.baomidou</groupId>
<artifactId>lock4j-redisson-spring-boot-starter</artifactId>
</dependency>
+
+ <dependency>
+ <groupId>com.github.ben-manes.caffeine</groupId>
+ <artifactId>caffeine</artifactId>
+ </dependency>
+
+ <dependency>
+ <groupId>com.fasterxml.jackson.datatype</groupId>
+ <artifactId>jackson-datatype-jsr310</artifactId>
+ </dependency>
</dependencies>
</project>
diff --git a/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/config/CacheConfig.java b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/config/CacheConfig.java
new file mode 100644
index 0000000..d57ba4e
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/config/CacheConfig.java
@@ -0,0 +1,45 @@
+package org.dromara.common.redis.config;
+
+import com.github.benmanes.caffeine.cache.Cache;
+import com.github.benmanes.caffeine.cache.Caffeine;
+import org.dromara.common.redis.manager.PlusSpringCacheManager;
+import org.springframework.boot.autoconfigure.AutoConfiguration;
+import org.springframework.cache.CacheManager;
+import org.springframework.cache.annotation.EnableCaching;
+import org.springframework.context.annotation.Bean;
+
+import java.util.concurrent.TimeUnit;
+
+/**
+ * 缂撳瓨閰嶇疆
+ *
+ * @author Lion Li
+ */
+@AutoConfiguration
+@EnableCaching
+public class CacheConfig {
+
+ /**
+ * caffeine 鏈湴缂撳瓨澶勭悊鍣�
+ */
+ @Bean
+ public Cache<Object, Object> caffeine() {
+ return Caffeine.newBuilder()
+ // 璁剧疆鏈�鍚庝竴娆″啓鍏ユ垨璁块棶鍚庣粡杩囧浐瀹氭椂闂磋繃鏈�
+ .expireAfterWrite(30, TimeUnit.SECONDS)
+ // 鍒濆鐨勭紦瀛樼┖闂村ぇ灏�
+ .initialCapacity(100)
+ // 缂撳瓨鐨勬渶澶ф潯鏁�
+ .maximumSize(1000)
+ .build();
+ }
+
+ /**
+ * 鑷畾涔夌紦瀛樼鐞嗗櫒 鏁村悎spring-cache
+ */
+ @Bean
+ public CacheManager cacheManager() {
+ return new PlusSpringCacheManager();
+ }
+
+}
diff --git a/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/config/RedisConfig.java b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/config/RedisConfig.java
index 7999f2b..f8fe79a 100644
--- a/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/config/RedisConfig.java
+++ b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/config/RedisConfig.java
@@ -5,10 +5,14 @@
import com.fasterxml.jackson.annotation.PropertyAccessor;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.jsontype.impl.LaissezFaireSubTypeValidator;
+import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
+import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateTimeDeserializer;
+import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateTimeSerializer;
import lombok.extern.slf4j.Slf4j;
+import org.dromara.common.core.utils.SpringUtils;
import org.dromara.common.redis.config.properties.RedissonProperties;
import org.dromara.common.redis.handler.KeyPrefixHandler;
-import org.dromara.common.redis.manager.PlusSpringCacheManager;
+import org.dromara.common.redis.handler.RedisExceptionHandler;
import org.redisson.client.codec.StringCodec;
import org.redisson.codec.CompositeCodec;
import org.redisson.codec.TypedJsonJacksonCodec;
@@ -16,9 +20,12 @@
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.AutoConfiguration;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
-import org.springframework.cache.CacheManager;
-import org.springframework.cache.annotation.EnableCaching;
import org.springframework.context.annotation.Bean;
+import org.springframework.core.task.VirtualThreadTaskExecutor;
+
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+import java.util.TimeZone;
/**
* redis閰嶇疆
@@ -27,20 +34,22 @@
*/
@Slf4j
@AutoConfiguration
-@EnableCaching
@EnableConfigurationProperties(RedissonProperties.class)
public class RedisConfig {
@Autowired
private RedissonProperties redissonProperties;
- @Autowired
- private ObjectMapper objectMapper;
-
@Bean
public RedissonAutoConfigurationCustomizer redissonCustomizer() {
return config -> {
- ObjectMapper om = objectMapper.copy();
+ JavaTimeModule javaTimeModule = new JavaTimeModule();
+ DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
+ javaTimeModule.addSerializer(LocalDateTime.class, new LocalDateTimeSerializer(formatter));
+ javaTimeModule.addDeserializer(LocalDateTime.class, new LocalDateTimeDeserializer(formatter));
+ ObjectMapper om = new ObjectMapper();
+ om.registerModule(javaTimeModule);
+ om.setTimeZone(TimeZone.getDefault());
om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
// 鎸囧畾搴忓垪鍖栬緭鍏ョ殑绫诲瀷锛岀被蹇呴』鏄潪final淇グ鐨勩�傚簭鍒楀寲鏃跺皢瀵硅薄鍏ㄧ被鍚嶄竴璧蜂繚瀛樹笅鏉�
om.activateDefaultTyping(LaissezFaireSubTypeValidator.instance, ObjectMapper.DefaultTyping.NON_FINAL);
@@ -52,6 +61,9 @@
// 缂撳瓨 Lua 鑴氭湰 鍑忓皯缃戠粶浼犺緭(redisson 澶ч儴鍒嗙殑鍔熻兘閮芥槸鍩轰簬 Lua 鑴氭湰瀹炵幇)
.setUseScriptCache(true)
.setCodec(codec);
+ if (SpringUtils.isVirtual()) {
+ config.setNettyExecutor(new VirtualThreadTaskExecutor("redisson-"));
+ }
RedissonProperties.SingleServerConfig singleServerConfig = redissonProperties.getSingleServerConfig();
if (ObjectUtil.isNotNull(singleServerConfig)) {
// 浣跨敤鍗曟満妯″紡
@@ -87,11 +99,11 @@
}
/**
- * 鑷畾涔夌紦瀛樼鐞嗗櫒 鏁村悎spring-cache
+ * 寮傚父澶勭悊鍣�
*/
@Bean
- public CacheManager cacheManager() {
- return new PlusSpringCacheManager();
+ public RedisExceptionHandler redisExceptionHandler() {
+ return new RedisExceptionHandler();
}
/**
diff --git a/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/handler/RedisExceptionHandler.java b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/handler/RedisExceptionHandler.java
new file mode 100644
index 0000000..5ed12a6
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/handler/RedisExceptionHandler.java
@@ -0,0 +1,30 @@
+package org.dromara.common.redis.handler;
+
+import cn.hutool.http.HttpStatus;
+import com.baomidou.lock.exception.LockFailureException;
+import jakarta.servlet.http.HttpServletRequest;
+import lombok.extern.slf4j.Slf4j;
+import org.dromara.common.core.domain.R;
+import org.springframework.web.bind.annotation.ExceptionHandler;
+import org.springframework.web.bind.annotation.RestControllerAdvice;
+
+/**
+ * Redis寮傚父澶勭悊鍣�
+ *
+ * @author AprilWind
+ */
+@Slf4j
+@RestControllerAdvice
+public class RedisExceptionHandler {
+
+ /**
+ * 鍒嗗竷寮忛攣Lock4j寮傚父
+ */
+ @ExceptionHandler(LockFailureException.class)
+ public R<Void> handleLockFailureException(LockFailureException e, HttpServletRequest request) {
+ String requestURI = request.getRequestURI();
+ log.error("鑾峰彇閿佸け璐ヤ簡'{}',鍙戠敓Lock4j寮傚父." + requestURI, e.getMessage());
+ return R.fail(HttpStatus.HTTP_UNAVAILABLE, "涓氬姟澶勭悊涓紝璇风◢鍚庡啀璇�...");
+ }
+
+}
diff --git a/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/manager/CaffeineCacheDecorator.java b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/manager/CaffeineCacheDecorator.java
new file mode 100644
index 0000000..ee1d405
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/manager/CaffeineCacheDecorator.java
@@ -0,0 +1,90 @@
+package org.dromara.common.redis.manager;
+
+import org.dromara.common.core.utils.SpringUtils;
+import org.springframework.cache.Cache;
+
+import java.util.concurrent.Callable;
+
+/**
+ * Cache 瑁呴グ鍣ㄦā寮�(鐢ㄤ簬鎵╁睍 Caffeine 涓�绾х紦瀛�)
+ *
+ * @author LionLi
+ */
+public class CaffeineCacheDecorator implements Cache {
+
+ private static final com.github.benmanes.caffeine.cache.Cache<Object, Object>
+ CAFFEINE = SpringUtils.getBean("caffeine");
+
+ private final Cache cache;
+
+ public CaffeineCacheDecorator(Cache cache) {
+ this.cache = cache;
+ }
+
+ @Override
+ public String getName() {
+ return cache.getName();
+ }
+
+ @Override
+ public Object getNativeCache() {
+ return cache.getNativeCache();
+ }
+
+ public String getUniqueKey(Object key) {
+ return cache.getName() + ":" + key;
+ }
+
+ @Override
+ public ValueWrapper get(Object key) {
+ Object o = CAFFEINE.get(getUniqueKey(key), k -> cache.get(key));
+ return (ValueWrapper) o;
+ }
+
+ @SuppressWarnings("unchecked")
+ public <T> T get(Object key, Class<T> type) {
+ Object o = CAFFEINE.get(getUniqueKey(key), k -> cache.get(key, type));
+ return (T) o;
+ }
+
+ @Override
+ public void put(Object key, Object value) {
+ CAFFEINE.invalidate(getUniqueKey(key));
+ cache.put(key, value);
+ }
+
+ public ValueWrapper putIfAbsent(Object key, Object value) {
+ CAFFEINE.invalidate(getUniqueKey(key));
+ return cache.putIfAbsent(key, value);
+ }
+
+ @Override
+ public void evict(Object key) {
+ evictIfPresent(key);
+ }
+
+ public boolean evictIfPresent(Object key) {
+ boolean b = cache.evictIfPresent(key);
+ if (b) {
+ CAFFEINE.invalidate(getUniqueKey(key));
+ }
+ return b;
+ }
+
+ @Override
+ public void clear() {
+ cache.clear();
+ }
+
+ public boolean invalidate() {
+ return cache.invalidate();
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public <T> T get(Object key, Callable<T> valueLoader) {
+ Object o = CAFFEINE.get(getUniqueKey(key), k -> cache.get(key, valueLoader));
+ return (T) o;
+ }
+
+}
diff --git a/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/manager/PlusSpringCacheManager.java b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/manager/PlusSpringCacheManager.java
index 08ebc78..a48cb14 100644
--- a/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/manager/PlusSpringCacheManager.java
+++ b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/manager/PlusSpringCacheManager.java
@@ -156,7 +156,7 @@
private Cache createMap(String name, CacheConfig config) {
RMap<Object, Object> map = RedisUtils.getClient().getMap(name);
- Cache cache = new RedissonCache(map, allowNullValues);
+ Cache cache = new CaffeineCacheDecorator(new RedissonCache(map, allowNullValues));
if (transactionAware) {
cache = new TransactionAwareCacheDecorator(cache);
}
@@ -170,7 +170,7 @@
private Cache createMapCache(String name, CacheConfig config) {
RMapCache<Object, Object> map = RedisUtils.getClient().getMapCache(name);
- Cache cache = new RedissonCache(map, config, allowNullValues);
+ Cache cache = new CaffeineCacheDecorator(new RedissonCache(map, config, allowNullValues));
if (transactionAware) {
cache = new TransactionAwareCacheDecorator(cache);
}
diff --git a/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/utils/RedisUtils.java b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/utils/RedisUtils.java
index ce32055..67be2fb 100644
--- a/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/utils/RedisUtils.java
+++ b/ruoyi-common/ruoyi-common-redis/src/main/java/org/dromara/common/redis/utils/RedisUtils.java
@@ -65,6 +65,12 @@
consumer.accept(msg);
}
+ /**
+ * 鍙戝竷娑堟伅鍒版寚瀹氱殑棰戦亾
+ *
+ * @param channelKey 閫氶亾key
+ * @param msg 鍙戦�佹暟鎹�
+ */
public static <T> void publish(String channelKey, T msg) {
RTopic topic = CLIENT.getTopic(channelKey);
topic.publish(msg);
@@ -107,7 +113,11 @@
bucket.setAndKeepTTL(value);
} catch (Exception e) {
long timeToLive = bucket.remainTimeToLive();
- setCacheObject(key, value, Duration.ofMillis(timeToLive));
+ if (timeToLive == -1) {
+ setCacheObject(key, value);
+ } else {
+ setCacheObject(key, value, Duration.ofMillis(timeToLive));
+ }
}
} else {
bucket.set(value);
diff --git a/ruoyi-common/ruoyi-common-redis/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports b/ruoyi-common/ruoyi-common-redis/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
index 59192c5..0475b19 100644
--- a/ruoyi-common/ruoyi-common-redis/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
+++ b/ruoyi-common/ruoyi-common-redis/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
@@ -1 +1,2 @@
org.dromara.common.redis.config.RedisConfig
+org.dromara.common.redis.config.CacheConfig
diff --git a/ruoyi-common/ruoyi-common-satoken/pom.xml b/ruoyi-common/ruoyi-common-satoken/pom.xml
index 01c282b..4df7d4d 100644
--- a/ruoyi-common/ruoyi-common-satoken/pom.xml
+++ b/ruoyi-common/ruoyi-common-satoken/pom.xml
@@ -36,6 +36,11 @@
<artifactId>sa-token-jwt</artifactId>
</dependency>
+ <dependency>
+ <groupId>com.github.ben-manes.caffeine</groupId>
+ <artifactId>caffeine</artifactId>
+ </dependency>
+
</dependencies>
</project>
diff --git a/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/config/SaTokenConfig.java b/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/config/SaTokenConfig.java
index ce8d85c..61c6b9a 100644
--- a/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/config/SaTokenConfig.java
+++ b/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/config/SaTokenConfig.java
@@ -7,6 +7,7 @@
import org.dromara.common.core.factory.YmlPropertySourceFactory;
import org.dromara.common.satoken.core.dao.PlusSaTokenDao;
import org.dromara.common.satoken.core.service.SaPermissionImpl;
+import org.dromara.common.satoken.handler.SaTokenExceptionHandler;
import org.springframework.boot.autoconfigure.AutoConfiguration;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.PropertySource;
@@ -42,4 +43,12 @@
return new PlusSaTokenDao();
}
+ /**
+ * 寮傚父澶勭悊鍣�
+ */
+ @Bean
+ public SaTokenExceptionHandler saTokenExceptionHandler() {
+ return new SaTokenExceptionHandler();
+ }
+
}
diff --git a/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/core/dao/PlusSaTokenDao.java b/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/core/dao/PlusSaTokenDao.java
index d885962..0664755 100644
--- a/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/core/dao/PlusSaTokenDao.java
+++ b/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/core/dao/PlusSaTokenDao.java
@@ -2,26 +2,42 @@
import cn.dev33.satoken.dao.SaTokenDao;
import cn.dev33.satoken.util.SaFoxUtil;
+import cn.hutool.core.lang.Console;
+import com.github.benmanes.caffeine.cache.Cache;
+import com.github.benmanes.caffeine.cache.Caffeine;
import org.dromara.common.redis.utils.RedisUtils;
import java.time.Duration;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
+import java.util.concurrent.TimeUnit;
/**
* Sa-Token鎸佷箙灞傛帴鍙�(浣跨敤妗嗘灦鑷甫RedisUtils瀹炵幇 鍗忚缁熶竴)
+ * <p>
+ * 閲囩敤 caffeine + redis 澶氱骇缂撳瓨 浼樺寲骞跺彂鏌ヨ鏁堢巼
*
* @author Lion Li
*/
public class PlusSaTokenDao implements SaTokenDao {
+
+ private static final Cache<String, Object> CAFFEINE = Caffeine.newBuilder()
+ // 璁剧疆鏈�鍚庝竴娆″啓鍏ユ垨璁块棶鍚庣粡杩囧浐瀹氭椂闂磋繃鏈�
+ .expireAfterWrite(5, TimeUnit.SECONDS)
+ // 鍒濆鐨勭紦瀛樼┖闂村ぇ灏�
+ .initialCapacity(100)
+ // 缂撳瓨鐨勬渶澶ф潯鏁�
+ .maximumSize(1000)
+ .build();
/**
* 鑾峰彇Value锛屽鏃犺繑绌�
*/
@Override
public String get(String key) {
- return RedisUtils.getCacheObject(key);
+ Object o = CAFFEINE.get(key, k -> RedisUtils.getCacheObject(key));
+ return (String) o;
}
/**
@@ -38,6 +54,7 @@
} else {
RedisUtils.setCacheObject(key, value, Duration.ofSeconds(timeout));
}
+ CAFFEINE.put(key, value);
}
/**
@@ -47,6 +64,7 @@
public void update(String key, String value) {
if (RedisUtils.hasKey(key)) {
RedisUtils.setCacheObject(key, value, true);
+ CAFFEINE.put(key, value);
}
}
@@ -81,7 +99,8 @@
*/
@Override
public Object getObject(String key) {
- return RedisUtils.getCacheObject(key);
+ Object o = CAFFEINE.get(key, k -> RedisUtils.getCacheObject(key));
+ return o;
}
/**
@@ -98,6 +117,7 @@
} else {
RedisUtils.setCacheObject(key, object, Duration.ofSeconds(timeout));
}
+ CAFFEINE.put(key, object);
}
/**
@@ -107,6 +127,7 @@
public void updateObject(String key, Object object) {
if (RedisUtils.hasKey(key)) {
RedisUtils.setCacheObject(key, object, true);
+ CAFFEINE.put(key, object);
}
}
@@ -139,10 +160,14 @@
/**
* 鎼滅储鏁版嵁
*/
+ @SuppressWarnings("unchecked")
@Override
public List<String> searchData(String prefix, String keyword, int start, int size, boolean sortType) {
- Collection<String> keys = RedisUtils.keys(prefix + "*" + keyword + "*");
- List<String> list = new ArrayList<>(keys);
- return SaFoxUtil.searchList(list, start, size, sortType);
+ String keyStr = prefix + "*" + keyword + "*";
+ return (List<String>) CAFFEINE.get(keyStr, k -> {
+ Collection<String> keys = RedisUtils.keys(keyStr);
+ List<String> list = new ArrayList<>(keys);
+ return SaFoxUtil.searchList(list, start, size, sortType);
+ });
}
}
diff --git a/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/handler/SaTokenExceptionHandler.java b/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/handler/SaTokenExceptionHandler.java
new file mode 100644
index 0000000..a45af89
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/handler/SaTokenExceptionHandler.java
@@ -0,0 +1,52 @@
+package org.dromara.common.satoken.handler;
+
+import cn.dev33.satoken.exception.NotLoginException;
+import cn.dev33.satoken.exception.NotPermissionException;
+import cn.dev33.satoken.exception.NotRoleException;
+import cn.hutool.http.HttpStatus;
+import jakarta.servlet.http.HttpServletRequest;
+import lombok.extern.slf4j.Slf4j;
+import org.dromara.common.core.domain.R;
+import org.springframework.web.bind.annotation.ExceptionHandler;
+import org.springframework.web.bind.annotation.RestControllerAdvice;
+
+/**
+ * SaToken寮傚父澶勭悊鍣�
+ *
+ * @author Lion Li
+ */
+@Slf4j
+@RestControllerAdvice
+public class SaTokenExceptionHandler {
+
+ /**
+ * 鏉冮檺鐮佸紓甯�
+ */
+ @ExceptionHandler(NotPermissionException.class)
+ public R<Void> handleNotPermissionException(NotPermissionException e, HttpServletRequest request) {
+ String requestURI = request.getRequestURI();
+ log.error("璇锋眰鍦板潃'{}',鏉冮檺鐮佹牎楠屽け璐�'{}'", requestURI, e.getMessage());
+ return R.fail(HttpStatus.HTTP_FORBIDDEN, "娌℃湁璁块棶鏉冮檺锛岃鑱旂郴绠$悊鍛樻巿鏉�");
+ }
+
+ /**
+ * 瑙掕壊鏉冮檺寮傚父
+ */
+ @ExceptionHandler(NotRoleException.class)
+ public R<Void> handleNotRoleException(NotRoleException e, HttpServletRequest request) {
+ String requestURI = request.getRequestURI();
+ log.error("璇锋眰鍦板潃'{}',瑙掕壊鏉冮檺鏍¢獙澶辫触'{}'", requestURI, e.getMessage());
+ return R.fail(HttpStatus.HTTP_FORBIDDEN, "娌℃湁璁块棶鏉冮檺锛岃鑱旂郴绠$悊鍛樻巿鏉�");
+ }
+
+ /**
+ * 璁よ瘉澶辫触
+ */
+ @ExceptionHandler(NotLoginException.class)
+ public R<Void> handleNotLoginException(NotLoginException e, HttpServletRequest request) {
+ String requestURI = request.getRequestURI();
+ log.error("璇锋眰鍦板潃'{}',璁よ瘉澶辫触'{}',鏃犳硶璁块棶绯荤粺璧勬簮", requestURI, e.getMessage());
+ return R.fail(HttpStatus.HTTP_UNAUTHORIZED, "璁よ瘉澶辫触锛屾棤娉曡闂郴缁熻祫婧�");
+ }
+
+}
diff --git a/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/utils/LoginHelper.java b/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/utils/LoginHelper.java
index 8488ac1..1e0d8a7 100644
--- a/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/utils/LoginHelper.java
+++ b/ruoyi-common/ruoyi-common-satoken/src/main/java/org/dromara/common/satoken/utils/LoginHelper.java
@@ -1,7 +1,5 @@
package org.dromara.common.satoken.utils;
-import cn.dev33.satoken.context.SaHolder;
-import cn.dev33.satoken.context.model.SaStorage;
import cn.dev33.satoken.session.SaSession;
import cn.dev33.satoken.stp.SaLoginModel;
import cn.dev33.satoken.stp.StpUtil;
@@ -15,7 +13,6 @@
import org.dromara.common.core.enums.UserType;
import java.util.Set;
-import java.util.function.Supplier;
/**
* 鐧诲綍閴存潈鍔╂墜
@@ -35,9 +32,11 @@
public static final String LOGIN_USER_KEY = "loginUser";
public static final String TENANT_KEY = "tenantId";
public static final String USER_KEY = "userId";
+ public static final String USER_NAME_KEY = "userName";
public static final String DEPT_KEY = "deptId";
+ public static final String DEPT_NAME_KEY = "deptName";
+ public static final String DEPT_CATEGORY_KEY = "deptCategory";
public static final String CLIENT_KEY = "clientid";
- public static final String TENANT_ADMIN_KEY = "isTenantAdmin";
/**
* 鐧诲綍绯荤粺 鍩轰簬 璁惧绫诲瀷
@@ -47,32 +46,27 @@
* @param model 閰嶇疆鍙傛暟
*/
public static void login(LoginUser loginUser, SaLoginModel model) {
- SaStorage storage = SaHolder.getStorage();
- storage.set(LOGIN_USER_KEY, loginUser);
- storage.set(TENANT_KEY, loginUser.getTenantId());
- storage.set(USER_KEY, loginUser.getUserId());
- storage.set(DEPT_KEY, loginUser.getDeptId());
model = ObjectUtil.defaultIfNull(model, new SaLoginModel());
StpUtil.login(loginUser.getLoginId(),
model.setExtra(TENANT_KEY, loginUser.getTenantId())
.setExtra(USER_KEY, loginUser.getUserId())
- .setExtra(DEPT_KEY, loginUser.getDeptId()));
- SaSession tokenSession = StpUtil.getTokenSession();
- tokenSession.updateTimeout(model.getTimeout());
- tokenSession.set(LOGIN_USER_KEY, loginUser);
+ .setExtra(USER_NAME_KEY, loginUser.getUsername())
+ .setExtra(DEPT_KEY, loginUser.getDeptId())
+ .setExtra(DEPT_NAME_KEY, loginUser.getDeptName())
+ .setExtra(DEPT_CATEGORY_KEY, loginUser.getDeptCategory())
+ );
+ StpUtil.getTokenSession().set(LOGIN_USER_KEY, loginUser);
}
/**
* 鑾峰彇鐢ㄦ埛(澶氱骇缂撳瓨)
*/
public static LoginUser getLoginUser() {
- return (LoginUser) getStorageIfAbsentSet(LOGIN_USER_KEY, () -> {
- SaSession session = StpUtil.getTokenSession();
- if (ObjectUtil.isNull(session)) {
- return null;
- }
- return session.get(LOGIN_USER_KEY);
- });
+ SaSession session = StpUtil.getTokenSession();
+ if (ObjectUtil.isNull(session)) {
+ return null;
+ }
+ return (LoginUser) session.get(LOGIN_USER_KEY);
}
/**
@@ -90,7 +84,7 @@
* 鑾峰彇鐢ㄦ埛id
*/
public static Long getUserId() {
- return Convert.toLong(getExtra(USER_KEY));
+ return Convert.toLong(getExtra(USER_KEY));
}
/**
@@ -107,8 +101,32 @@
return Convert.toLong(getExtra(DEPT_KEY));
}
+ /**
+ * 鑾峰彇閮ㄩ棬鍚�
+ */
+ public static String getDeptName() {
+ return Convert.toStr(getExtra(DEPT_NAME_KEY));
+ }
+
+ /**
+ * 鑾峰彇閮ㄩ棬绫诲埆缂栫爜
+ */
+ public static String getDeptCategory() {
+ return Convert.toStr(getExtra(DEPT_CATEGORY_KEY));
+ }
+
+ /**
+ * 鑾峰彇褰撳墠 Token 鐨勬墿灞曚俊鎭�
+ *
+ * @param key 閿��
+ * @return 瀵瑰簲鐨勬墿灞曟暟鎹�
+ */
private static Object getExtra(String key) {
- return getStorageIfAbsentSet(key, () -> StpUtil.getExtra(key));
+ try {
+ return StpUtil.getExtra(key);
+ } catch (Exception e) {
+ return null;
+ }
}
/**
@@ -136,12 +154,17 @@
return UserConstants.SUPER_ADMIN_ID.equals(userId);
}
+ /**
+ * 鏄惁涓鸿秴绾х鐞嗗憳
+ *
+ * @return 缁撴灉
+ */
public static boolean isSuperAdmin() {
return isSuperAdmin(getUserId());
}
/**
- * 鏄惁涓鸿秴绾х鐞嗗憳
+ * 鏄惁涓虹鎴风鐞嗗憳
*
* @param rolePermission 瑙掕壊鏉冮檺鏍囪瘑缁�
* @return 缁撴灉
@@ -150,27 +173,22 @@
return rolePermission.contains(TenantConstants.TENANT_ADMIN_ROLE_KEY);
}
+ /**
+ * 鏄惁涓虹鎴风鐞嗗憳
+ *
+ * @return 缁撴灉
+ */
public static boolean isTenantAdmin() {
- Object value = getStorageIfAbsentSet(TENANT_ADMIN_KEY, () -> {
- return isTenantAdmin(getLoginUser().getRolePermission());
- });
- return Convert.toBool(value);
+ return Convert.toBool(isTenantAdmin(getLoginUser().getRolePermission()));
}
+ /**
+ * 妫�鏌ュ綋鍓嶇敤鎴锋槸鍚﹀凡鐧诲綍
+ *
+ * @return 缁撴灉
+ */
public static boolean isLogin() {
return getLoginUser() != null;
}
- public static Object getStorageIfAbsentSet(String key, Supplier<Object> handle) {
- try {
- Object obj = SaHolder.getStorage().get(key);
- if (ObjectUtil.isNull(obj)) {
- obj = handle.get();
- SaHolder.getStorage().set(key, obj);
- }
- return obj;
- } catch (Exception e) {
- return null;
- }
- }
}
diff --git a/ruoyi-common/ruoyi-common-security/src/main/java/org/dromara/common/security/config/SecurityConfig.java b/ruoyi-common/ruoyi-common-security/src/main/java/org/dromara/common/security/config/SecurityConfig.java
index 63d7eb1..b9283e0 100644
--- a/ruoyi-common/ruoyi-common-security/src/main/java/org/dromara/common/security/config/SecurityConfig.java
+++ b/ruoyi-common/ruoyi-common-security/src/main/java/org/dromara/common/security/config/SecurityConfig.java
@@ -4,14 +4,14 @@
import cn.dev33.satoken.interceptor.SaInterceptor;
import cn.dev33.satoken.router.SaRouter;
import cn.dev33.satoken.stp.StpUtil;
+import lombok.RequiredArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
import org.dromara.common.core.utils.ServletUtils;
import org.dromara.common.core.utils.SpringUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.satoken.utils.LoginHelper;
import org.dromara.common.security.config.properties.SecurityProperties;
import org.dromara.common.security.handler.AllUrlHandler;
-import lombok.RequiredArgsConstructor;
-import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.autoconfigure.AutoConfiguration;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
@@ -38,35 +38,35 @@
public void addInterceptors(InterceptorRegistry registry) {
// 娉ㄥ唽璺敱鎷︽埅鍣紝鑷畾涔夐獙璇佽鍒�
registry.addInterceptor(new SaInterceptor(handler -> {
- AllUrlHandler allUrlHandler = SpringUtils.getBean(AllUrlHandler.class);
- // 鐧诲綍楠岃瘉 -- 鎺掗櫎澶氫釜璺緞
- SaRouter
- // 鑾峰彇鎵�鏈夌殑
- .match(allUrlHandler.getUrls())
- // 瀵规湭鎺掗櫎鐨勮矾寰勮繘琛屾鏌�
- .check(() -> {
- // 妫�鏌ユ槸鍚︾櫥褰� 鏄惁鏈塼oken
- StpUtil.checkLogin();
+ AllUrlHandler allUrlHandler = SpringUtils.getBean(AllUrlHandler.class);
+ // 鐧诲綍楠岃瘉 -- 鎺掗櫎澶氫釜璺緞
+ SaRouter
+ // 鑾峰彇鎵�鏈夌殑
+ .match(allUrlHandler.getUrls())
+ // 瀵规湭鎺掗櫎鐨勮矾寰勮繘琛屾鏌�
+ .check(() -> {
+ // 妫�鏌ユ槸鍚︾櫥褰� 鏄惁鏈塼oken
+ StpUtil.checkLogin();
- // 妫�鏌� header 涓� param 閲岀殑 clientid 涓� token 閲岀殑鏄惁涓�鑷�
- String headerCid = ServletUtils.getRequest().getHeader(LoginHelper.CLIENT_KEY);
- String paramCid = ServletUtils.getParameter(LoginHelper.CLIENT_KEY);
- String clientId = StpUtil.getExtra(LoginHelper.CLIENT_KEY).toString();
- if (!StringUtils.equalsAny(clientId, headerCid, paramCid)) {
- // token 鏃犳晥
- throw NotLoginException.newInstance(StpUtil.getLoginType(),
- "-100", "瀹㈡埛绔疘D涓嶵oken涓嶅尮閰�",
- StpUtil.getTokenValue());
- }
+ // 妫�鏌� header 涓� param 閲岀殑 clientid 涓� token 閲岀殑鏄惁涓�鑷�
+ String headerCid = ServletUtils.getRequest().getHeader(LoginHelper.CLIENT_KEY);
+ String paramCid = ServletUtils.getParameter(LoginHelper.CLIENT_KEY);
+ String clientId = StpUtil.getExtra(LoginHelper.CLIENT_KEY).toString();
+ if (!StringUtils.equalsAny(clientId, headerCid, paramCid)) {
+ // token 鏃犳晥
+ throw NotLoginException.newInstance(StpUtil.getLoginType(),
+ "-100", "瀹㈡埛绔疘D涓嶵oken涓嶅尮閰�",
+ StpUtil.getTokenValue());
+ }
- // 鏈夋晥鐜囧奖鍝� 鐢ㄤ簬涓存椂娴嬭瘯
- // if (log.isDebugEnabled()) {
- // log.info("鍓╀綑鏈夋晥鏃堕棿: {}", StpUtil.getTokenTimeout());
- // log.info("涓存椂鏈夋晥鏃堕棿: {}", StpUtil.getTokenActivityTimeout());
- // }
+ // 鏈夋晥鐜囧奖鍝� 鐢ㄤ簬涓存椂娴嬭瘯
+ // if (log.isDebugEnabled()) {
+ // log.info("鍓╀綑鏈夋晥鏃堕棿: {}", StpUtil.getTokenTimeout());
+ // log.info("涓存椂鏈夋晥鏃堕棿: {}", StpUtil.getTokenActivityTimeout());
+ // }
- });
- })).addPathPatterns("/**")
+ });
+ })).addPathPatterns("/**")
// 鎺掗櫎涓嶉渶瑕佹嫤鎴殑璺緞
.excludePathPatterns(securityProperties.getExcludes());
}
diff --git a/ruoyi-common/ruoyi-common-security/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports b/ruoyi-common/ruoyi-common-security/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
index f78c781..6def724 100644
--- a/ruoyi-common/ruoyi-common-security/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
+++ b/ruoyi-common/ruoyi-common-security/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
@@ -1,3 +1,2 @@
-org.dromara.common.security.handler.GlobalExceptionHandler
org.dromara.common.security.handler.AllUrlHandler
org.dromara.common.security.config.SecurityConfig
diff --git a/ruoyi-common/ruoyi-common-sms/pom.xml b/ruoyi-common/ruoyi-common-sms/pom.xml
index c50f222..932cb9d 100644
--- a/ruoyi-common/ruoyi-common-sms/pom.xml
+++ b/ruoyi-common/ruoyi-common-sms/pom.xml
@@ -20,13 +20,12 @@
<dependency>
<groupId>org.dromara.sms4j</groupId>
<artifactId>sms4j-spring-boot-starter</artifactId>
- <exclusions>
- <!-- 鎺掗櫎浜笢鐭俊鍐呭瓨鍦ㄧ殑fastjson绛夊緟浣滆�呭悗缁慨澶� -->
- <exclusion>
- <groupId>com.alibaba</groupId>
- <artifactId>fastjson</artifactId>
- </exclusion>
- </exclusions>
+ </dependency>
+
+ <!-- RuoYi Common Redis-->
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-redis</artifactId>
</dependency>
</dependencies>
diff --git a/ruoyi-common/ruoyi-common-sms/src/main/java/org/dromara/common/sms/config/SmsAutoConfiguration.java b/ruoyi-common/ruoyi-common-sms/src/main/java/org/dromara/common/sms/config/SmsAutoConfiguration.java
index 29f60fc..1e88407 100644
--- a/ruoyi-common/ruoyi-common-sms/src/main/java/org/dromara/common/sms/config/SmsAutoConfiguration.java
+++ b/ruoyi-common/ruoyi-common-sms/src/main/java/org/dromara/common/sms/config/SmsAutoConfiguration.java
@@ -1,14 +1,24 @@
package org.dromara.common.sms.config;
+import org.dromara.common.sms.core.dao.PlusSmsDao;
+import org.dromara.sms4j.api.dao.SmsDao;
import org.springframework.boot.autoconfigure.AutoConfiguration;
+import org.springframework.boot.autoconfigure.data.redis.RedisAutoConfiguration;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Primary;
/**
- * 鐭俊閰嶇疆绫�(鏆傛椂娌$敤 棰勭暀鎵╁睍)
+ * 鐭俊閰嶇疆绫�
*
- * @author Lion Li
- * @version 4.2.0
+ * @author Feng
*/
-@AutoConfiguration
+@AutoConfiguration(after = {RedisAutoConfiguration.class})
public class SmsAutoConfiguration {
+ @Primary
+ @Bean
+ public SmsDao smsDao() {
+ return new PlusSmsDao();
+ }
+
}
diff --git a/ruoyi-common/ruoyi-common-sms/src/main/java/org/dromara/common/sms/core/dao/PlusSmsDao.java b/ruoyi-common/ruoyi-common-sms/src/main/java/org/dromara/common/sms/core/dao/PlusSmsDao.java
new file mode 100644
index 0000000..91d8d24
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-sms/src/main/java/org/dromara/common/sms/core/dao/PlusSmsDao.java
@@ -0,0 +1,72 @@
+package org.dromara.common.sms.core.dao;
+
+import org.dromara.common.core.constant.GlobalConstants;
+import org.dromara.common.redis.utils.RedisUtils;
+import org.dromara.sms4j.api.dao.SmsDao;
+
+import java.time.Duration;
+
+/**
+ * SmsDao缂撳瓨閰嶇疆 (浣跨敤妗嗘灦鑷甫RedisUtils瀹炵幇 鍗忚缁熶竴)
+ * <p>涓昏鐢ㄤ簬鐭俊閲嶈瘯鍜屾嫤鎴殑缂撳瓨
+ *
+ * @author Feng
+ */
+public class PlusSmsDao implements SmsDao {
+
+ /**
+ * 瀛樺偍
+ *
+ * @param key 閿�
+ * @param value 鍊�
+ * @param cacheTime 缂撳瓨鏃堕棿锛堝崟浣嶏細绉�)
+ */
+ @Override
+ public void set(String key, Object value, long cacheTime) {
+ RedisUtils.setCacheObject(GlobalConstants.GLOBAL_REDIS_KEY + key, value, Duration.ofSeconds(cacheTime));
+ }
+
+ /**
+ * 瀛樺偍
+ *
+ * @param key 閿�
+ * @param value 鍊�
+ */
+ @Override
+ public void set(String key, Object value) {
+ RedisUtils.setCacheObject(GlobalConstants.GLOBAL_REDIS_KEY + key, value, true);
+ }
+
+ /**
+ * 璇诲彇
+ *
+ * @param key 閿�
+ * @return 鍊�
+ */
+ @Override
+ public Object get(String key) {
+ return RedisUtils.getCacheObject(GlobalConstants.GLOBAL_REDIS_KEY + key);
+ }
+
+ /**
+ * remove
+ * <p> 鏍规嵁key绉婚櫎缂撳瓨
+ *
+ * @param key 缂撳瓨閿�
+ * @return 琚垹闄ょ殑value
+ * @author :Wind
+ */
+ @Override
+ public Object remove(String key) {
+ return RedisUtils.deleteObject(GlobalConstants.GLOBAL_REDIS_KEY + key);
+ }
+
+ /**
+ * 娓呯┖
+ */
+ @Override
+ public void clean() {
+ RedisUtils.deleteObject(GlobalConstants.GLOBAL_REDIS_KEY + "sms:");
+ }
+
+}
diff --git a/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialLoginConfigProperties.java b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialLoginConfigProperties.java
index 76be234..5f49d9c 100644
--- a/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialLoginConfigProperties.java
+++ b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialLoginConfigProperties.java
@@ -2,6 +2,8 @@
import lombok.Data;
+import java.util.List;
+
/**
* 绀句氦鐧诲綍閰嶇疆
*
@@ -65,4 +67,9 @@
*/
private String serverUrl;
+ /**
+ * 璇锋眰鑼冨洿
+ */
+ private List<String> scopes;
+
}
diff --git a/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialProperties.java b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialProperties.java
index 1beb7d0..1487a6a 100644
--- a/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialProperties.java
+++ b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/config/properties/SocialProperties.java
@@ -17,11 +17,6 @@
public class SocialProperties {
/**
- * 鏄惁鍚敤
- */
- private Boolean enabled;
-
- /**
* 鎺堟潈绫诲瀷
*/
private Map<String, SocialLoginConfigProperties> type;
diff --git a/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/topiam/AuthTopIamRequest.java b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/topiam/AuthTopIamRequest.java
new file mode 100644
index 0000000..13649f9
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/topiam/AuthTopIamRequest.java
@@ -0,0 +1,100 @@
+package org.dromara.common.social.topiam;
+
+import cn.hutool.core.lang.Dict;
+import cn.hutool.core.util.StrUtil;
+import com.xkcoding.http.support.HttpHeader;
+import lombok.extern.slf4j.Slf4j;
+import me.zhyd.oauth.cache.AuthStateCache;
+import me.zhyd.oauth.config.AuthConfig;
+import me.zhyd.oauth.exception.AuthException;
+import me.zhyd.oauth.model.AuthCallback;
+import me.zhyd.oauth.model.AuthToken;
+import me.zhyd.oauth.model.AuthUser;
+import me.zhyd.oauth.request.AuthDefaultRequest;
+import me.zhyd.oauth.utils.HttpUtils;
+import me.zhyd.oauth.utils.UrlBuilder;
+import org.dromara.common.core.utils.SpringUtils;
+import org.dromara.common.json.utils.JsonUtils;
+
+import static org.dromara.common.social.topiam.AuthTopiamSource.TOPIAM;
+
+/**
+ * TopIAM 璁よ瘉璇锋眰
+ *
+ * @author xlsea
+ * @since 2024-01-06
+ */
+@Slf4j
+public class AuthTopIamRequest extends AuthDefaultRequest {
+
+ public static final String SERVER_URL = SpringUtils.getProperty("justauth.type.topiam.server-url");
+
+ /**
+ * 璁惧畾褰掑睘鍩�
+ */
+ public AuthTopIamRequest(AuthConfig config) {
+ super(config, TOPIAM);
+ }
+
+ public AuthTopIamRequest(AuthConfig config, AuthStateCache authStateCache) {
+ super(config, TOPIAM, authStateCache);
+ }
+
+ @Override
+ protected AuthToken getAccessToken(AuthCallback authCallback) {
+ String body = doPostAuthorizationCode(authCallback.getCode());
+ Dict object = JsonUtils.parseMap(body);
+ checkResponse(object);
+ return AuthToken.builder()
+ .accessToken(object.getStr("access_token"))
+ .refreshToken(object.getStr("refresh_token"))
+ .idToken(object.getStr("id_token"))
+ .tokenType(object.getStr("token_type"))
+ .scope(object.getStr("scope"))
+ .build();
+ }
+
+ @Override
+ protected AuthUser getUserInfo(AuthToken authToken) {
+ String body = doGetUserInfo(authToken);
+ Dict object = JsonUtils.parseMap(body);
+ checkResponse(object);
+ return AuthUser.builder()
+ .uuid(object.getStr("sub"))
+ .username(object.getStr("preferred_username"))
+ .nickname(object.getStr("nickname"))
+ .avatar(object.getStr("picture"))
+ .email(object.getStr("email"))
+ .token(authToken)
+ .source(source.toString())
+ .build();
+ }
+
+
+ @Override
+ protected String doGetUserInfo(AuthToken authToken) {
+ return new HttpUtils(config.getHttpConfig()).get(source.userInfo(), null, new HttpHeader()
+ .add("Content-Type", "application/json")
+ .add("Authorization", "Bearer " + authToken.getAccessToken()), false).getBody();
+ }
+
+
+ @Override
+ public String authorize(String state) {
+ return UrlBuilder.fromBaseUrl(super.authorize(state))
+ .queryParam("scope", StrUtil.join("%20", config.getScopes()))
+ .build();
+ }
+
+ public static void checkResponse(Dict object) {
+ // oauth/token 楠岃瘉寮傚父
+ if (object.containsKey("error")) {
+ throw new AuthException(object.getStr("error_description"));
+ }
+ // user 楠岃瘉寮傚父
+ if (object.containsKey("message")) {
+ throw new AuthException(object.getStr("message"));
+ }
+ }
+
+}
diff --git a/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/topiam/AuthTopiamSource.java b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/topiam/AuthTopiamSource.java
new file mode 100644
index 0000000..e47d6c6
--- /dev/null
+++ b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/topiam/AuthTopiamSource.java
@@ -0,0 +1,51 @@
+package org.dromara.common.social.topiam;
+
+import me.zhyd.oauth.config.AuthSource;
+import me.zhyd.oauth.request.AuthDefaultRequest;
+
+/**
+ * Oauth2 榛樿鎺ュ彛璇存槑
+ *
+ * @author xlsea
+ * @since 2024-01-06
+ */
+public enum AuthTopiamSource implements AuthSource {
+
+ /**
+ * 娴嬭瘯
+ */
+ TOPIAM {
+ /**
+ * 鎺堟潈鐨刟pi
+ */
+ @Override
+ public String authorize() {
+ return AuthTopIamRequest.SERVER_URL + "/oauth2/auth";
+ }
+
+ /**
+ * 鑾峰彇accessToken鐨刟pi
+ */
+ @Override
+ public String accessToken() {
+ return AuthTopIamRequest.SERVER_URL + "/oauth2/token";
+ }
+
+ /**
+ * 鑾峰彇鐢ㄦ埛淇℃伅鐨刟pi
+ */
+ @Override
+ public String userInfo() {
+ return AuthTopIamRequest.SERVER_URL + "/oauth2/userinfo";
+ }
+
+ /**
+ * 骞冲彴瀵瑰簲鐨� AuthRequest 瀹炵幇绫伙紝蹇呴』缁ф壙鑷� {@link AuthDefaultRequest}
+ */
+ @Override
+ public Class<? extends AuthDefaultRequest> getTargetClass() {
+ return AuthTopIamRequest.class;
+ }
+
+ }
+}
diff --git a/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/utils/SocialUtils.java b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/utils/SocialUtils.java
index 51b7e13..04f6214 100644
--- a/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/utils/SocialUtils.java
+++ b/ruoyi-common/ruoyi-common-social/src/main/java/org/dromara/common/social/utils/SocialUtils.java
@@ -11,6 +11,7 @@
import org.dromara.common.social.config.properties.SocialLoginConfigProperties;
import org.dromara.common.social.config.properties.SocialProperties;
import org.dromara.common.social.maxkey.AuthMaxKeyRequest;
+import org.dromara.common.social.topiam.AuthTopIamRequest;
/**
* 璁よ瘉鎺堟潈宸ュ叿绫�
@@ -38,7 +39,8 @@
AuthConfig.AuthConfigBuilder builder = AuthConfig.builder()
.clientId(obj.getClientId())
.clientSecret(obj.getClientSecret())
- .redirectUri(obj.getRedirectUri());
+ .redirectUri(obj.getRedirectUri())
+ .scopes(obj.getScopes());
return switch (source.toLowerCase()) {
case "dingtalk" -> new AuthDingTalkRequest(builder.build(), STATE_CACHE);
case "baidu" -> new AuthBaiduRequest(builder.build(), STATE_CACHE);
@@ -63,6 +65,7 @@
case "wechat_mp" -> new AuthWeChatMpRequest(builder.build(), STATE_CACHE);
case "aliyun" -> new AuthAliyunRequest(builder.build(), STATE_CACHE);
case "maxkey" -> new AuthMaxKeyRequest(builder.build(), STATE_CACHE);
+ case "topiam" -> new AuthTopIamRequest(builder.build(), STATE_CACHE);
default -> throw new AuthException("鏈幏鍙栧埌鏈夋晥鐨凙uth閰嶇疆");
};
}
diff --git a/ruoyi-common/ruoyi-common-tenant/pom.xml b/ruoyi-common/ruoyi-common-tenant/pom.xml
index 2b87bf9..8e1a6ab 100644
--- a/ruoyi-common/ruoyi-common-tenant/pom.xml
+++ b/ruoyi-common/ruoyi-common-tenant/pom.xml
@@ -19,16 +19,12 @@
<dependency>
<groupId>org.dromara</groupId>
<artifactId>ruoyi-common-mybatis</artifactId>
+ <optional>true</optional>
</dependency>
<dependency>
<groupId>org.dromara</groupId>
<artifactId>ruoyi-common-redis</artifactId>
- </dependency>
-
- <dependency>
- <groupId>com.alibaba</groupId>
- <artifactId>transmittable-thread-local</artifactId>
</dependency>
</dependencies>
diff --git a/ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/config/TenantConfig.java b/ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/config/TenantConfig.java
index 8610641..3fb99c5 100644
--- a/ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/config/TenantConfig.java
+++ b/ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/config/TenantConfig.java
@@ -2,8 +2,6 @@
import cn.dev33.satoken.dao.SaTokenDao;
import cn.hutool.core.util.ObjectUtil;
-import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
-import com.baomidou.mybatisplus.extension.plugins.inner.InnerInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.TenantLineInnerInterceptor;
import org.dromara.common.core.utils.reflect.ReflectUtils;
import org.dromara.common.mybatis.config.MybatisPlusConfig;
@@ -18,14 +16,12 @@
import org.redisson.config.SingleServerConfig;
import org.redisson.spring.starter.RedissonAutoConfigurationCustomizer;
import org.springframework.boot.autoconfigure.AutoConfiguration;
+import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.cache.CacheManager;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Primary;
-
-import java.util.ArrayList;
-import java.util.List;
/**
* 绉熸埛閰嶇疆绫�
@@ -33,29 +29,22 @@
* @author Lion Li
*/
@EnableConfigurationProperties(TenantProperties.class)
-@AutoConfiguration(after = {RedisConfig.class, MybatisPlusConfig.class})
+@AutoConfiguration(after = {RedisConfig.class})
@ConditionalOnProperty(value = "tenant.enable", havingValue = "true")
public class TenantConfig {
- /**
- * 鍒濆鍖栫鎴烽厤缃�
- */
- @Bean
- public boolean tenantInit(MybatisPlusInterceptor mybatisPlusInterceptor,
- TenantProperties tenantProperties) {
- List<InnerInterceptor> interceptors = new ArrayList<>();
- // 澶氱鎴锋彃浠� 蹇呴』鏀惧埌绗竴浣�
- interceptors.add(tenantLineInnerInterceptor(tenantProperties));
- interceptors.addAll(mybatisPlusInterceptor.getInterceptors());
- mybatisPlusInterceptor.setInterceptors(interceptors);
- return true;
- }
+ @ConditionalOnBean(MybatisPlusConfig.class)
+ @AutoConfiguration(after = {MybatisPlusConfig.class})
+ static class MybatisPlusConfigation {
- /**
- * 澶氱鎴锋彃浠�
- */
- public TenantLineInnerInterceptor tenantLineInnerInterceptor(TenantProperties tenantProperties) {
- return new TenantLineInnerInterceptor(new PlusTenantLineHandler(tenantProperties));
+ /**
+ * 澶氱鎴锋彃浠�
+ */
+ @Bean
+ public TenantLineInnerInterceptor tenantLineInnerInterceptor(TenantProperties tenantProperties) {
+ return new TenantLineInnerInterceptor(new PlusTenantLineHandler(tenantProperties));
+ }
+
}
@Bean
diff --git a/ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/handle/TenantKeyPrefixHandler.java b/ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/handle/TenantKeyPrefixHandler.java
index 14dad1a..9475398 100644
--- a/ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/handle/TenantKeyPrefixHandler.java
+++ b/ruoyi-common/ruoyi-common-tenant/src/main/java/org/dromara/common/tenant/handle/TenantKeyPrefixHandler.java
@@ -1,5 +1,6 @@
package org.dromara.common.tenant.handle;
+import com.baomidou.mybatisplus.core.plugins.InterceptorIgnoreHelper;
import lombok.extern.slf4j.Slf4j;
import org.dromara.common.core.constant.GlobalConstants;
import org.dromara.common.core.utils.StringUtils;
@@ -26,6 +27,9 @@
if (StringUtils.isBlank(name)) {
return null;
}
+ if (InterceptorIgnoreHelper.willIgnoreTenantLine("")) {
+ return super.map(name);
+ }
if (StringUtils.contains(name, GlobalConstants.GLOBAL_REDIS_KEY)) {
return super.map(name);
}
@@ -49,6 +53,9 @@
if (StringUtils.isBlank(unmap)) {
return null;
}
+ if (InterceptorIgnoreHelper.willIgnoreTenantLine("")) {
+ return super.unmap(name);
+ }
if (StringUtils.contains(name, GlobalConstants.GLOBAL_REDIS_KEY)) {
return super.unmap(name);
}
diff --git a/ruoyi-common/ruoyi-common-translation/src/main/java/org/dromara/common/translation/core/impl/NicknameTranslationImpl.java b/ruoyi-common/ruoyi-common-translation/src/main/java/org/dromara/common/translation/core/impl/NicknameTranslationImpl.java
index ac65f5a..b92c7f0 100644
--- a/ruoyi-common/ruoyi-common-translation/src/main/java/org/dromara/common/translation/core/impl/NicknameTranslationImpl.java
+++ b/ruoyi-common/ruoyi-common-translation/src/main/java/org/dromara/common/translation/core/impl/NicknameTranslationImpl.java
@@ -20,7 +20,9 @@
@Override
public String translation(Object key, String other) {
if (key instanceof Long id) {
- return userService.selectNicknameById(id);
+ return userService.selectNicknameByIds(id.toString());
+ } else if (key instanceof String ids) {
+ return userService.selectNicknameByIds(ids);
}
return null;
}
diff --git a/ruoyi-common/ruoyi-common-web/pom.xml b/ruoyi-common/ruoyi-common-web/pom.xml
index 293c522..b250fa9 100644
--- a/ruoyi-common/ruoyi-common-web/pom.xml
+++ b/ruoyi-common/ruoyi-common-web/pom.xml
@@ -57,11 +57,6 @@
<groupId>cn.hutool</groupId>
<artifactId>hutool-crypto</artifactId>
</dependency>
-
- <dependency>
- <groupId>com.alibaba</groupId>
- <artifactId>transmittable-thread-local</artifactId>
- </dependency>
</dependencies>
</project>
diff --git a/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/CaptchaConfig.java b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/CaptchaConfig.java
index 9225a51..650517e 100644
--- a/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/CaptchaConfig.java
+++ b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/CaptchaConfig.java
@@ -23,7 +23,7 @@
private static final int WIDTH = 160;
private static final int HEIGHT = 60;
- private static final Color BACKGROUND = Color.PINK;
+ private static final Color BACKGROUND = Color.LIGHT_GRAY;
private static final Font FONT = new Font("Arial", Font.BOLD, 48);
/**
diff --git a/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/ResourcesConfig.java b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/ResourcesConfig.java
index 1b78ebc..1371913 100644
--- a/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/ResourcesConfig.java
+++ b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/ResourcesConfig.java
@@ -1,5 +1,6 @@
package org.dromara.common.web.config;
+import org.dromara.common.web.handler.GlobalExceptionHandler;
import org.dromara.common.web.interceptor.PlusWebInvokeTimeInterceptor;
import org.springframework.boot.autoconfigure.AutoConfiguration;
import org.springframework.context.annotation.Bean;
@@ -49,4 +50,12 @@
// 杩斿洖鏂扮殑CorsFilter
return new CorsFilter(source);
}
+
+ /**
+ * 鍏ㄥ眬寮傚父澶勭悊鍣�
+ */
+ @Bean
+ public GlobalExceptionHandler globalExceptionHandler() {
+ return new GlobalExceptionHandler();
+ }
}
diff --git a/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/UndertowConfig.java b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/UndertowConfig.java
index 421ce6d..0f78928 100644
--- a/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/UndertowConfig.java
+++ b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/config/UndertowConfig.java
@@ -2,9 +2,11 @@
import io.undertow.server.DefaultByteBufferPool;
import io.undertow.websockets.jsr.WebSocketDeploymentInfo;
+import org.dromara.common.core.utils.SpringUtils;
import org.springframework.boot.autoconfigure.AutoConfiguration;
import org.springframework.boot.web.embedded.undertow.UndertowServletWebServerFactory;
import org.springframework.boot.web.server.WebServerFactoryCustomizer;
+import org.springframework.core.task.VirtualThreadTaskExecutor;
/**
* Undertow 鑷畾涔夐厤缃�
@@ -24,6 +26,12 @@
WebSocketDeploymentInfo webSocketDeploymentInfo = new WebSocketDeploymentInfo();
webSocketDeploymentInfo.setBuffers(new DefaultByteBufferPool(false, 512));
deploymentInfo.addServletContextAttribute("io.undertow.websockets.jsr.WebSocketDeploymentInfo", webSocketDeploymentInfo);
+ // 浣跨敤铏氭嫙绾跨▼
+ if (SpringUtils.isVirtual()) {
+ VirtualThreadTaskExecutor executor = new VirtualThreadTaskExecutor("undertow-");
+ deploymentInfo.setExecutor(executor);
+ deploymentInfo.setAsyncExecutor(executor);
+ }
});
}
diff --git a/ruoyi-common/ruoyi-common-security/src/main/java/org/dromara/common/security/handler/GlobalExceptionHandler.java b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/handler/GlobalExceptionHandler.java
similarity index 77%
rename from ruoyi-common/ruoyi-common-security/src/main/java/org/dromara/common/security/handler/GlobalExceptionHandler.java
rename to ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/handler/GlobalExceptionHandler.java
index a4dcfe3..bd47c18 100644
--- a/ruoyi-common/ruoyi-common-security/src/main/java/org/dromara/common/security/handler/GlobalExceptionHandler.java
+++ b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/handler/GlobalExceptionHandler.java
@@ -1,8 +1,5 @@
-package org.dromara.common.security.handler;
+package org.dromara.common.web.handler;
-import cn.dev33.satoken.exception.NotLoginException;
-import cn.dev33.satoken.exception.NotPermissionException;
-import cn.dev33.satoken.exception.NotRoleException;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.http.HttpStatus;
import jakarta.servlet.http.HttpServletRequest;
@@ -21,6 +18,7 @@
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;
import org.springframework.web.method.annotation.MethodArgumentTypeMismatchException;
+import org.springframework.web.servlet.NoHandlerFoundException;
/**
* 鍏ㄥ眬寮傚父澶勭悊鍣�
@@ -32,36 +30,6 @@
public class GlobalExceptionHandler {
/**
- * 鏉冮檺鐮佸紓甯�
- */
- @ExceptionHandler(NotPermissionException.class)
- public R<Void> handleNotPermissionException(NotPermissionException e, HttpServletRequest request) {
- String requestURI = request.getRequestURI();
- log.error("璇锋眰鍦板潃'{}',鏉冮檺鐮佹牎楠屽け璐�'{}'", requestURI, e.getMessage());
- return R.fail(HttpStatus.HTTP_FORBIDDEN, "娌℃湁璁块棶鏉冮檺锛岃鑱旂郴绠$悊鍛樻巿鏉�");
- }
-
- /**
- * 瑙掕壊鏉冮檺寮傚父
- */
- @ExceptionHandler(NotRoleException.class)
- public R<Void> handleNotRoleException(NotRoleException e, HttpServletRequest request) {
- String requestURI = request.getRequestURI();
- log.error("璇锋眰鍦板潃'{}',瑙掕壊鏉冮檺鏍¢獙澶辫触'{}'", requestURI, e.getMessage());
- return R.fail(HttpStatus.HTTP_FORBIDDEN, "娌℃湁璁块棶鏉冮檺锛岃鑱旂郴绠$悊鍛樻巿鏉�");
- }
-
- /**
- * 璁よ瘉澶辫触
- */
- @ExceptionHandler(NotLoginException.class)
- public R<Void> handleNotLoginException(NotLoginException e, HttpServletRequest request) {
- String requestURI = request.getRequestURI();
- log.error("璇锋眰鍦板潃'{}',璁よ瘉澶辫触'{}',鏃犳硶璁块棶绯荤粺璧勬簮", requestURI, e.getMessage());
- return R.fail(HttpStatus.HTTP_UNAUTHORIZED, "璁よ瘉澶辫触锛屾棤娉曡闂郴缁熻祫婧�");
- }
-
- /**
* 璇锋眰鏂瑰紡涓嶆敮鎸�
*/
@ExceptionHandler(HttpRequestMethodNotSupportedException.class)
@@ -69,7 +37,7 @@
HttpServletRequest request) {
String requestURI = request.getRequestURI();
log.error("璇锋眰鍦板潃'{}',涓嶆敮鎸�'{}'璇锋眰", requestURI, e.getMethod());
- return R.fail(e.getMessage());
+ return R.fail(HttpStatus.HTTP_BAD_METHOD, e.getMessage());
}
/**
@@ -112,6 +80,16 @@
}
/**
+ * 鎵句笉鍒拌矾鐢�
+ */
+ @ExceptionHandler(NoHandlerFoundException.class)
+ public R<Void> handleNoHandlerFoundException(NoHandlerFoundException e, HttpServletRequest request) {
+ String requestURI = request.getRequestURI();
+ log.error("璇锋眰鍦板潃'{}'涓嶅瓨鍦�.", requestURI);
+ return R.fail(HttpStatus.HTTP_NOT_FOUND, e.getMessage());
+ }
+
+ /**
* 鎷︽埅鏈煡鐨勮繍琛屾椂寮傚父
*/
@ExceptionHandler(RuntimeException.class)
diff --git a/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/interceptor/PlusWebInvokeTimeInterceptor.java b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/interceptor/PlusWebInvokeTimeInterceptor.java
index 1b4ce3d..12c8086 100644
--- a/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/interceptor/PlusWebInvokeTimeInterceptor.java
+++ b/ruoyi-common/ruoyi-common-web/src/main/java/org/dromara/common/web/interceptor/PlusWebInvokeTimeInterceptor.java
@@ -2,15 +2,14 @@
import cn.hutool.core.io.IoUtil;
import cn.hutool.core.map.MapUtil;
-import com.alibaba.ttl.TransmittableThreadLocal;
-import org.dromara.common.core.utils.SpringUtils;
-import org.dromara.common.core.utils.StringUtils;
-import org.dromara.common.json.utils.JsonUtils;
-import org.dromara.common.web.filter.RepeatedlyRequestWrapper;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.time.StopWatch;
+import org.dromara.common.core.utils.SpringUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.json.utils.JsonUtils;
+import org.dromara.common.web.filter.RepeatedlyRequestWrapper;
import org.springframework.http.MediaType;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
@@ -30,7 +29,7 @@
private final String prodProfile = "prod";
- private final TransmittableThreadLocal<StopWatch> invokeTimeTL = new TransmittableThreadLocal<>();
+ private final static ThreadLocal<StopWatch> KEY_CACHE = new ThreadLocal<>();
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
@@ -56,7 +55,7 @@
}
StopWatch stopWatch = new StopWatch();
- invokeTimeTL.set(stopWatch);
+ KEY_CACHE.set(stopWatch);
stopWatch.start();
}
return true;
@@ -70,10 +69,10 @@
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
if (!prodProfile.equals(SpringUtils.getActiveProfile())) {
- StopWatch stopWatch = invokeTimeTL.get();
+ StopWatch stopWatch = KEY_CACHE.get();
stopWatch.stop();
log.info("[PLUS]缁撴潫璇锋眰 => URL[{}],鑰楁椂:[{}]姣", request.getMethod() + " " + request.getRequestURI(), stopWatch.getTime());
- invokeTimeTL.remove();
+ KEY_CACHE.remove();
}
}
diff --git a/ruoyi-extend/pom.xml b/ruoyi-extend/pom.xml
index f5348cc..d7280ce 100644
--- a/ruoyi-extend/pom.xml
+++ b/ruoyi-extend/pom.xml
@@ -13,7 +13,7 @@
<modules>
<module>ruoyi-monitor-admin</module>
- <module>ruoyi-powerjob-server</module>
+ <module>ruoyi-snailjob-server</module>
</modules>
</project>
diff --git a/ruoyi-extend/ruoyi-monitor-admin/Dockerfile b/ruoyi-extend/ruoyi-monitor-admin/Dockerfile
index 7ae0682..a54f816 100644
--- a/ruoyi-extend/ruoyi-monitor-admin/Dockerfile
+++ b/ruoyi-extend/ruoyi-monitor-admin/Dockerfile
@@ -13,5 +13,6 @@
ADD ./target/ruoyi-monitor-admin.jar ./app.jar
-ENTRYPOINT java -Djava.security.egd=file:/dev/./urandom -jar app.jar \
- -XX:+HeapDumpOnOutOfMemoryError -Xlog:gc*,:time,tags,level -XX:+UseZGC ${JAVA_OPTS}
+ENTRYPOINT java -Djava.security.egd=file:/dev/./urandom \
+ -XX:+HeapDumpOnOutOfMemoryError -XX:+UseZGC ${JAVA_OPTS} \
+ -jar app.jar
diff --git a/ruoyi-extend/ruoyi-monitor-admin/src/main/java/org/dromara/monitor/admin/config/AdminServerConfig.java b/ruoyi-extend/ruoyi-monitor-admin/src/main/java/org/dromara/monitor/admin/config/AdminServerConfig.java
index 1f70c75..53d248e 100644
--- a/ruoyi-extend/ruoyi-monitor-admin/src/main/java/org/dromara/monitor/admin/config/AdminServerConfig.java
+++ b/ruoyi-extend/ruoyi-monitor-admin/src/main/java/org/dromara/monitor/admin/config/AdminServerConfig.java
@@ -3,7 +3,7 @@
import de.codecentric.boot.admin.server.config.EnableAdminServer;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.task.TaskExecutionAutoConfiguration;
-import org.springframework.boot.task.TaskExecutorBuilder;
+import org.springframework.boot.task.ThreadPoolTaskExecutorBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Lazy;
@@ -23,7 +23,7 @@
@Lazy
@Bean(name = TaskExecutionAutoConfiguration.APPLICATION_TASK_EXECUTOR_BEAN_NAME)
@ConditionalOnMissingBean(Executor.class)
- public ThreadPoolTaskExecutor applicationTaskExecutor(TaskExecutorBuilder builder) {
+ public ThreadPoolTaskExecutor applicationTaskExecutor(ThreadPoolTaskExecutorBuilder builder) {
return builder.build();
}
diff --git a/ruoyi-extend/ruoyi-powerjob-server/Dockerfile b/ruoyi-extend/ruoyi-powerjob-server/Dockerfile
deleted file mode 100644
index 729bb22..0000000
--- a/ruoyi-extend/ruoyi-powerjob-server/Dockerfile
+++ /dev/null
@@ -1,17 +0,0 @@
-#FROM findepi/graalvm:java17-native
-FROM openjdk:17.0.2-oraclelinux8
-
-MAINTAINER Lion Li
-
-RUN mkdir -p /ruoyi/powerjob/logs
-
-WORKDIR /ruoyi/powerjob
-
-ENV LANG=C.UTF-8 LC_ALL=C.UTF-8 JAVA_OPTS="-Xms512m -Xmx1024m"
-
-EXPOSE 7700
-
-ADD ./target/ruoyi-powerjob-server.jar ./app.jar
-
-ENTRYPOINT java -Djava.security.egd=file:/dev/./urandom -jar app.jar \
- -XX:+HeapDumpOnOutOfMemoryError -Xlog:gc*,:time,tags,level -XX:+UseZGC ${JAVA_OPTS}
diff --git a/ruoyi-extend/ruoyi-powerjob-server/pom.xml b/ruoyi-extend/ruoyi-powerjob-server/pom.xml
deleted file mode 100644
index bdb92a4..0000000
--- a/ruoyi-extend/ruoyi-powerjob-server/pom.xml
+++ /dev/null
@@ -1,68 +0,0 @@
-<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
- <parent>
- <groupId>org.dromara</groupId>
- <artifactId>ruoyi-extend</artifactId>
- <version>${revision}</version>
- </parent>
- <modelVersion>4.0.0</modelVersion>
- <packaging>jar</packaging>
- <artifactId>ruoyi-powerjob-server</artifactId>
-
- <properties>
- <spring-boot.version>2.7.18</spring-boot.version>
- <spring-boot-admin.version>2.7.11</spring-boot-admin.version>
- </properties>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.springframework.boot</groupId>
- <artifactId>spring-boot-starter-parent</artifactId>
- <version>${spring-boot.version}</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
-
- <dependencies>
-
- <!-- PowerJob server-->
- <dependency>
- <groupId>tech.powerjob</groupId>
- <artifactId>powerjob-server-starter</artifactId>
- <version>${powerjob.version}</version>
- </dependency>
-
- <dependency>
- <groupId>de.codecentric</groupId>
- <artifactId>spring-boot-admin-starter-client</artifactId>
- <version>${spring-boot-admin.version}</version>
- </dependency>
-
- <dependency>
- <groupId>org.projectlombok</groupId>
- <artifactId>lombok</artifactId>
- </dependency>
-
- </dependencies>
-
- <build>
- <finalName>${project.artifactId}</finalName>
- <plugins>
- <plugin>
- <groupId>org.springframework.boot</groupId>
- <artifactId>spring-boot-maven-plugin</artifactId>
- <version>${spring-boot.version}</version>
- <executions>
- <execution>
- <goals>
- <goal>repackage</goal>
- </goals>
- </execution>
- </executions>
- </plugin>
- </plugins>
- </build>
-
-</project>
diff --git a/ruoyi-extend/ruoyi-powerjob-server/src/main/java/org/dromara/powerjob/PowerJobServerApplication.java b/ruoyi-extend/ruoyi-powerjob-server/src/main/java/org/dromara/powerjob/PowerJobServerApplication.java
deleted file mode 100644
index 3898639..0000000
--- a/ruoyi-extend/ruoyi-powerjob-server/src/main/java/org/dromara/powerjob/PowerJobServerApplication.java
+++ /dev/null
@@ -1,25 +0,0 @@
-package org.dromara.powerjob;
-
-import lombok.extern.slf4j.Slf4j;
-import org.springframework.boot.SpringApplication;
-import org.springframework.boot.autoconfigure.SpringBootApplication;
-import org.springframework.scheduling.annotation.EnableScheduling;
-import tech.powerjob.server.common.utils.PropertyUtils;
-
-/**
- * powerjob 鍚姩绋嬪簭
- *
- * @author yhan219
- */
-@Slf4j
-@EnableScheduling
-@SpringBootApplication(scanBasePackages = "tech.powerjob.server")
-public class PowerJobServerApplication {
-
- public static void main(String[] args) {
- PropertyUtils.init();
- SpringApplication.run(tech.powerjob.server.PowerJobServerApplication.class, args);
- log.info("鏂囨。鍦板潃: https://www.yuque.com/powerjob/guidence/problem");
- }
-
-}
diff --git a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/application-dev.properties b/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/application-dev.properties
deleted file mode 100644
index ba024d3..0000000
--- a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/application-dev.properties
+++ /dev/null
@@ -1,50 +0,0 @@
-oms.env=dev
-
-####### Database properties(Configure according to the the environment) #######
-spring.datasource.core.driver-class-name=com.mysql.cj.jdbc.Driver
-spring.datasource.core.jdbc-url=jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai&allowPublicKeyRetrieval=true
-spring.datasource.core.username=root
-spring.datasource.core.password=root
-spring.datasource.core.maximum-pool-size=20
-spring.datasource.core.minimum-idle=5
-
-# 鐩戞帶閰嶇疆
-# 瀹㈡埛绔紑鍏�
-spring.boot.admin.client.enabled=true
-# 璁剧疆 Spring Boot Admin Server 鍦板潃
-spring.boot.admin.client.url: http://localhost:9090/admin
-spring.boot.admin.client.instance.service-host-type=IP
-spring.boot.admin.client.username=ruoyi
-spring.boot.admin.client.password=123456
-
-####### MongoDB properties(Non-core configuration properties) #######
-####### delete mongodb config to disable mongodb #######
-oms.mongodb.enable=false
-#spring.data.mongodb.uri=mongodb+srv://zqq:No1Bug2Please3!@cluster0.wie54.gcp.mongodb.net/powerjob_daily?retryWrites=true&w=majority
-
-####### Email properties(Non-core configuration properties) #######
-####### Delete the following code to disable the mail #######
-#spring.mail.host=smtp.163.com
-#spring.mail.username=zqq@163.com
-#spring.mail.password=GOFZPNARMVKCGONV
-#spring.mail.properties.mail.smtp.auth=true
-#spring.mail.properties.mail.smtp.starttls.enable=true
-#spring.mail.properties.mail.smtp.starttls.required=true
-
-####### DingTalk properties(Non-core configuration properties) #######
-####### Delete the following code to disable the DingTalk #######
-#oms.alarm.ding.app-key=dingauqwkvxxnqskknfv
-#oms.alarm.ding.app-secret=XWrEPdAZMPgJeFtHuL0LH73LRj-74umF2_0BFcoXMfvnX0pCQvt0rpb1JOJU_HLl
-#oms.alarm.ding.agent-id=847044348
-
-####### Resource cleaning properties #######
-oms.instanceinfo.retention=1
-oms.container.retention.local=1
-oms.container.retention.remote=-1
-
-####### Cache properties #######
-oms.instance.metadata.cache.size=1024
-
-####### Threshold in precise fetching server(0~100). 100 means full detection of server, in which #######
-####### split-brain could be avoided while performance overhead would increase. #######
-oms.accurate.select.server.percentage = 50
diff --git a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/application-prod.properties b/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/application-prod.properties
deleted file mode 100644
index b13c688..0000000
--- a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/application-prod.properties
+++ /dev/null
@@ -1,50 +0,0 @@
-oms.env=prod
-
-####### Database properties(Configure according to the the environment) #######
-spring.datasource.core.driver-class-name=com.mysql.cj.jdbc.Driver
-spring.datasource.core.jdbc-url=jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai&allowPublicKeyRetrieval=true
-spring.datasource.core.username=root
-spring.datasource.core.password=root
-spring.datasource.core.maximum-pool-size=20
-spring.datasource.core.minimum-idle=5
-
-# 鐩戞帶閰嶇疆
-# 瀹㈡埛绔紑鍏�
-spring.boot.admin.client.enabled=true
-# 璁剧疆 Spring Boot Admin Server 鍦板潃
-spring.boot.admin.client.url: http://localhost:9090/admin
-spring.boot.admin.client.instance.service-host-type=IP
-spring.boot.admin.client.username=ruoyi
-spring.boot.admin.client.password=123456
-
-####### MongoDB properties(Non-core configuration properties) #######
-####### delete mongodb config to disable mongodb #######
-oms.mongodb.enable=false
-#spring.data.mongodb.uri=mongodb+srv://zqq:No1Bug2Please3!@cluster0.wie54.gcp.mongodb.net/powerjob_daily?retryWrites=true&w=majority
-
-####### Email properties(Non-core configuration properties) #######
-####### Delete the following code to disable the mail #######
-#spring.mail.host=smtp.163.com
-#spring.mail.username=zqq@163.com
-#spring.mail.password=GOFZPNARMVKCGONV
-#spring.mail.properties.mail.smtp.auth=true
-#spring.mail.properties.mail.smtp.starttls.enable=true
-#spring.mail.properties.mail.smtp.starttls.required=true
-
-####### DingTalk properties(Non-core configuration properties) #######
-####### Delete the following code to disable the DingTalk #######
-#oms.alarm.ding.app-key=dingauqwkvxxnqskknfv
-#oms.alarm.ding.app-secret=XWrEPdAZMPgJeFtHuL0LH73LRj-74umF2_0BFcoXMfvnX0pCQvt0rpb1JOJU_HLl
-#oms.alarm.ding.agent-id=847044348
-
-####### Resource cleaning properties #######
-oms.instanceinfo.retention=7
-oms.container.retention.local=7
-oms.container.retention.remote=-1
-
-####### Cache properties #######
-oms.instance.metadata.cache.size=2048
-
-####### Threshold in precise fetching server(0~100). 100 means full detection of server, in which #######
-####### split-brain could be avoided while performance overhead would increase. #######
-oms.accurate.select.server.percentage = 50
diff --git a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/application.properties b/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/application.properties
deleted file mode 100644
index 5b6516c..0000000
--- a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/application.properties
+++ /dev/null
@@ -1,33 +0,0 @@
-# Http server port
-server.port=7700
-
-spring.profiles.active=@profiles.active@
-spring.main.banner-mode=log
-spring.jpa.open-in-view=false
-spring.data.mongodb.repositories.type=none
-logging.level.org.mongodb=warn
-logging.level.tech.powerjob.server=warn
-logging.level.MONITOR_LOGGER_DB_OPERATION=warn
-logging.level.MONITOR_LOGGER_WORKER_HEART_BEAT=warn
-logging.config: classpath:logback-plus.xml
-
-# Configuration for uploading files.
-spring.servlet.multipart.enabled=true
-spring.servlet.multipart.file-size-threshold=0
-spring.servlet.multipart.max-file-size=209715200
-spring.servlet.multipart.max-request-size=209715200
-
-###### PowerJob transporter configuration ######
-oms.transporter.active.protocols=AKKA,HTTP
-oms.transporter.main.protocol=HTTP
-oms.akka.port=10086
-oms.http.port=10010
-# Prefix for all tables. Default empty string. Config if you have needs, i.e. pj_
-oms.table-prefix=pj_
-
-# Actuator 鐩戞帶绔偣鐨勯厤缃」
-spring.application.name: ruoyi-powerjob-server
-management.endpoints.web.exposure.include=*
-management.endpoint.health.show-details=ALWAYS
-management.endpoint.logfile.external-file=./logs/ruoyi-powerjob-server.log
-management.health.mongo.enabled=${oms.mongodb.enable}
diff --git a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/banner.txt b/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/banner.txt
deleted file mode 100644
index c0fac79..0000000
--- a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/banner.txt
+++ /dev/null
@@ -1,11 +0,0 @@
-Application Version: ${revision}
-Spring Boot Version: ${spring-boot.version}
- _ _
- (_) | |
- _ __ _____ _____ _ __ _ ___ | |__ ______ ___ ___ _ ____ _____ _ __
-| '_ \ / _ \ \ /\ / / _ \ '__| |/ _ \| '_ \______/ __|/ _ \ '__\ \ / / _ \ '__|
-| |_) | (_) \ V V / __/ | | | (_) | |_) | \__ \ __/ | \ V / __/ |
-| .__/ \___/ \_/\_/ \___|_| | |\___/|_.__/ |___/\___|_| \_/ \___|_|
-| | _/ |
-|_| |__/
-
diff --git a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/logback-plus.xml b/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/logback-plus.xml
deleted file mode 100644
index ad3bfa9..0000000
--- a/ruoyi-extend/ruoyi-powerjob-server/src/main/resources/logback-plus.xml
+++ /dev/null
@@ -1,34 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<configuration debug="false" scan="true" scanPeriod="1 seconds">
-
- <contextName>logback</contextName>
- <property name="log.path" value="./logs/ruoyi-powerjob-server"/>
- <property name="console.log.pattern"
- value="%red(%d{yyyy-MM-dd HH:mm:ss}) %green([%thread]) %highlight(%-5level) %boldMagenta(%logger{36}%n) - %msg%n"/>
- <property name="log.pattern" value="%d{yyyy-MM-dd HH:mm:ss} [%thread] %-5level %logger{36} - %msg%n"/>
-
- <appender name="console" class="ch.qos.logback.core.ConsoleAppender">
- <encoder>
- <pattern>${console.log.pattern}</pattern>
- <charset>utf-8</charset>
- </encoder>
- </appender>
-
- <appender name="file" class="ch.qos.logback.core.rolling.RollingFileAppender">
- <file>${log.path}.log</file>
- <rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
- <fileNamePattern>${log.path}.%d{yyyy-MM-dd}.log</fileNamePattern>
- <!-- 鏃ュ織鏈�澶х殑鍘嗗彶 60澶� -->
- <maxHistory>60</maxHistory>
- </rollingPolicy>
- <encoder>
- <pattern>${log.pattern}</pattern>
- </encoder>
- </appender>
-
- <root level="info">
- <appender-ref ref="console"/>
- <appender-ref ref="file"/>
- </root>
-
-</configuration>
diff --git a/ruoyi-extend/ruoyi-snailjob-server/Dockerfile b/ruoyi-extend/ruoyi-snailjob-server/Dockerfile
new file mode 100644
index 0000000..1fda8db
--- /dev/null
+++ b/ruoyi-extend/ruoyi-snailjob-server/Dockerfile
@@ -0,0 +1,19 @@
+#FROM findepi/graalvm:java17-native
+FROM openjdk:17.0.2-oraclelinux8
+
+MAINTAINER Lion Li
+
+RUN mkdir -p /ruoyi/snailjob/logs
+
+WORKDIR /ruoyi/snailjob
+
+ENV LANG=C.UTF-8 LC_ALL=C.UTF-8 JAVA_OPTS="-Xms512m -Xmx1024m"
+
+EXPOSE 8800
+EXPOSE 1788
+
+ADD ./target/ruoyi-snailjob-server.jar ./app.jar
+
+ENTRYPOINT java -Djava.security.egd=file:/dev/./urandom \
+ -XX:+HeapDumpOnOutOfMemoryError -XX:+UseZGC ${JAVA_OPTS} \
+ -jar app.jar
diff --git a/ruoyi-extend/ruoyi-snailjob-server/pom.xml b/ruoyi-extend/ruoyi-snailjob-server/pom.xml
new file mode 100644
index 0000000..7348b29
--- /dev/null
+++ b/ruoyi-extend/ruoyi-snailjob-server/pom.xml
@@ -0,0 +1,46 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ <parent>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-extend</artifactId>
+ <version>${revision}</version>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <packaging>jar</packaging>
+ <artifactId>ruoyi-snailjob-server</artifactId>
+
+ <dependencies>
+ <dependency>
+ <groupId>com.aizuda</groupId>
+ <artifactId>snail-job-server-starter</artifactId>
+ <version>${snailjob.version}</version>
+ </dependency>
+
+ <dependency>
+ <groupId>de.codecentric</groupId>
+ <artifactId>spring-boot-admin-starter-client</artifactId>
+ <version>${spring-boot-admin.version}</version>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <finalName>${project.artifactId}</finalName>
+ <plugins>
+ <plugin>
+ <groupId>org.springframework.boot</groupId>
+ <artifactId>spring-boot-maven-plugin</artifactId>
+ <version>${spring-boot.version}</version>
+ <executions>
+ <execution>
+ <goals>
+ <goal>repackage</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
+ </plugins>
+ </build>
+
+</project>
diff --git a/ruoyi-extend/ruoyi-snailjob-server/src/main/java/org/dromara/snailjob/SnailJobServerApplication.java b/ruoyi-extend/ruoyi-snailjob-server/src/main/java/org/dromara/snailjob/SnailJobServerApplication.java
new file mode 100644
index 0000000..dfab068
--- /dev/null
+++ b/ruoyi-extend/ruoyi-snailjob-server/src/main/java/org/dromara/snailjob/SnailJobServerApplication.java
@@ -0,0 +1,19 @@
+package org.dromara.snailjob;
+
+import org.springframework.boot.SpringApplication;
+import org.springframework.boot.autoconfigure.SpringBootApplication;
+
+/**
+ * SnailJob Server 鍚姩绋嬪簭
+ *
+ * @author opensnail
+ * @date 2024-05-17
+ */
+@SpringBootApplication
+public class SnailJobServerApplication {
+
+ public static void main(String[] args) {
+ SpringApplication.run(com.aizuda.snailjob.server.SnailJobServerApplication.class, args);
+ }
+
+}
diff --git a/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application-dev.yml b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application-dev.yml
new file mode 100644
index 0000000..be0b9b4
--- /dev/null
+++ b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application-dev.yml
@@ -0,0 +1,47 @@
+spring:
+ datasource:
+ type: com.zaxxer.hikari.HikariDataSource
+ driver-class-name: com.mysql.cj.jdbc.Driver
+ url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai&allowPublicKeyRetrieval=true
+ username: root
+ password: root
+ hikari:
+ connection-timeout: 30000
+ validation-timeout: 5000
+ minimum-idle: 10
+ maximum-pool-size: 20
+ idle-timeout: 600000
+ max-lifetime: 900000
+ keepaliveTime: 30000
+
+--- # snail-job 鏈嶅姟绔厤缃�
+snail-job:
+ # 鎷夊彇閲嶈瘯鏁版嵁鐨勬瘡鎵规鐨勫ぇ灏�
+ retry-pull-page-size: 1000
+ # 鎷夊彇閲嶈瘯鏁版嵁鐨勬瘡鎵规鐨勫ぇ灏�
+ job-pull-page-size: 1000
+ # 鏈嶅姟绔痭etty绔彛
+ netty-port: 1788
+ # 涓�涓鎴风姣忕鏈�澶氭帴鏀剁殑閲嶈瘯鏁伴噺鎸囦护
+ limiter: 1000
+ # 鍙锋妯″紡涓嬫闀块厤缃�
+ step: 100
+ # 鏃ュ織淇濆瓨鏃堕棿(鍗曚綅: day)
+ log-storage: 90
+ # 鍥炶皟閰嶇疆
+ callback:
+ #鍥炶皟鏈�澶ф墽琛屾鏁�
+ max-count: 288
+ #闂撮殧鏃堕棿
+ trigger-interval: 900
+ retry-max-pull-count: 10
+
+--- # 鐩戞帶涓績閰嶇疆
+spring.boot.admin.client:
+ # 澧炲姞瀹㈡埛绔紑鍏�
+ enabled: true
+ url: http://localhost:9090/admin
+ instance:
+ service-host-type: IP
+ username: ruoyi
+ password: 123456
diff --git a/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application-prod.yml b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application-prod.yml
new file mode 100644
index 0000000..4c69ee7
--- /dev/null
+++ b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application-prod.yml
@@ -0,0 +1,47 @@
+spring:
+ datasource:
+ type: com.zaxxer.hikari.HikariDataSource
+ driver-class-name: com.mysql.cj.jdbc.Driver
+ url: jdbc:mysql://localhost:3306/ry-vue?useUnicode=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai&allowPublicKeyRetrieval=true
+ username: root
+ password: root
+ hikari:
+ connection-timeout: 30000
+ validation-timeout: 5000
+ minimum-idle: 10
+ maximum-pool-size: 20
+ idle-timeout: 600000
+ max-lifetime: 900000
+ keepaliveTime: 30000
+
+--- # snail-job 鏈嶅姟绔厤缃�
+snail-job:
+ # 鎷夊彇閲嶈瘯鏁版嵁鐨勬瘡鎵规鐨勫ぇ灏�
+ retry-pull-page-size: 1000
+ # 鎷夊彇閲嶈瘯鏁版嵁鐨勬瘡鎵规鐨勫ぇ灏�
+ job-pull-page-size: 1000
+ # 鏈嶅姟绔� netty 绔彛
+ netty-port: 1788
+ # 涓�涓鎴风姣忕鏈�澶氭帴鏀剁殑閲嶈瘯鏁伴噺鎸囦护
+ limiter: 1000
+ # 鍙锋妯″紡涓嬫闀块厤缃�
+ step: 100
+ # 鏃ュ織淇濆瓨鏃堕棿(鍗曚綅: day)
+ log-storage: 90
+ # 鍥炶皟閰嶇疆
+ callback:
+ #鍥炶皟鏈�澶ф墽琛屾鏁�
+ max-count: 288
+ #闂撮殧鏃堕棿
+ trigger-interval: 900
+ retry-max-pull-count: 10
+
+--- # 鐩戞帶涓績閰嶇疆
+spring.boot.admin.client:
+ # 澧炲姞瀹㈡埛绔紑鍏�
+ enabled: true
+ url: http://localhost:9090/admin
+ instance:
+ service-host-type: IP
+ username: ruoyi
+ password: 123456
diff --git a/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application.yml b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application.yml
new file mode 100644
index 0000000..ba6df45
--- /dev/null
+++ b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/application.yml
@@ -0,0 +1,39 @@
+server:
+ port: 8800
+ servlet:
+ context-path: /snail-job
+
+spring:
+ application:
+ name: ruoyi-snailjob-server
+ profiles:
+ active: @profiles.active@
+ web:
+ resources:
+ static-locations: classpath:admin/
+
+mybatis-plus:
+ typeAliasesPackage: com.aizuda.snailjob.template.datasource.persistence.po
+ global-config:
+ db-config:
+ where-strategy: NOT_EMPTY
+ capital-mode: false
+ logic-delete-value: 1
+ logic-not-delete-value: 0
+ configuration:
+ map-underscore-to-camel-case: true
+ cache-enabled: true
+
+logging:
+ config: classpath:logback-plus.xml
+
+management:
+ endpoints:
+ web:
+ exposure:
+ include: '*'
+ endpoint:
+ health:
+ show-details: ALWAYS
+ logfile:
+ external-file: ./logs/ruoyi-snailjob-server/console.log
diff --git a/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/banner.txt b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/banner.txt
new file mode 100644
index 0000000..adb96c5
--- /dev/null
+++ b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/banner.txt
@@ -0,0 +1,11 @@
+Application Version: ${revision}
+Spring Boot Version: ${spring-boot.version}
+ _ _ _ _
+ (_) (_) | |
+ ___ _ __ __ _ _| |_ ___ | |__ ______ ___ ___ _ ____ _____ _ __
+/ __| '_ \ / _` | | | |/ _ \| '_ \______/ __|/ _ \ '__\ \ / / _ \ '__|
+\__ \ | | | (_| | | | | (_) | |_) | \__ \ __/ | \ V / __/ |
+|___/_| |_|\__,_|_|_| |\___/|_.__/ |___/\___|_| \_/ \___|_|
+ _/ |
+ |__/
+
diff --git a/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/logback-plus.xml b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/logback-plus.xml
new file mode 100644
index 0000000..a40262c
--- /dev/null
+++ b/ruoyi-extend/ruoyi-snailjob-server/src/main/resources/logback-plus.xml
@@ -0,0 +1,92 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<configuration>
+ <property name="log.path" value="./logs/ruoyi-snailjob-server" />
+ <property name="console.log.pattern"
+ value="%red(%d{yyyy-MM-dd HH:mm:ss}) %green([%thread]) %highlight(%-5level) %boldMagenta(%logger{36}%n) - %msg%n"/>
+ <property name="log.pattern" value="%d{yyyy-MM-dd HH:mm:ss} [%thread] %-5level %logger{36} - %msg%n"/>
+
+
+ <!-- 鎺у埗鍙拌緭鍑� -->
+ <appender name="console" class="ch.qos.logback.core.ConsoleAppender">
+ <encoder>
+ <pattern>${console.log.pattern}</pattern>
+ <charset>utf-8</charset>
+ </encoder>
+ </appender>
+
+ <!-- 鎺у埗鍙拌緭鍑� -->
+ <appender name="file_console" class="ch.qos.logback.core.rolling.RollingFileAppender">
+ <file>${log.path}/console.log</file>
+ <rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
+ <!-- 鏃ュ織鏂囦欢鍚嶆牸寮� -->
+ <fileNamePattern>${log.path}/console.%d{yyyy-MM-dd}.log</fileNamePattern>
+ <!-- 鏃ュ織鏈�澶� 1澶� -->
+ <maxHistory>1</maxHistory>
+ </rollingPolicy>
+ <encoder>
+ <pattern>${log.pattern}</pattern>
+ <charset>utf-8</charset>
+ </encoder>
+ <filter class="ch.qos.logback.classic.filter.ThresholdFilter">
+ <!-- 杩囨护鐨勭骇鍒� -->
+ <level>INFO</level>
+ </filter>
+ </appender>
+
+ <appender name="file_info" class="ch.qos.logback.core.rolling.RollingFileAppender">
+ <file>${log.path}/info.log</file>
+ <rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
+ <FileNamePattern>${log.path}/info.%d{yyyy-MM-dd}.log</FileNamePattern>
+ <MaxHistory>60</MaxHistory>
+ </rollingPolicy>
+ <encoder>
+ <pattern>${log.pattern}</pattern>
+ </encoder>
+ <filter class="ch.qos.logback.classic.filter.LevelFilter">
+ <level>INFO</level>
+ <onMatch>ACCEPT</onMatch>
+ <onMismatch>DENY</onMismatch>
+ </filter>
+ </appender>
+
+ <appender name="file_error" class="ch.qos.logback.core.rolling.RollingFileAppender">
+ <file>${log.path}/error.log</file>
+ <rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
+ <FileNamePattern>${log.path}/error.%d{yyyy-MM-dd}.log
+ </FileNamePattern>
+ <MaxHistory>60</MaxHistory>
+ </rollingPolicy>
+ <encoder>
+ <pattern>${log.pattern}</pattern>
+ </encoder>
+ <filter class="ch.qos.logback.classic.filter.LevelFilter">
+ <level>ERROR</level>
+ <onMatch>ACCEPT</onMatch>
+ <onMismatch>DENY</onMismatch>
+ </filter>
+ </appender>
+
+ <appender name ="async_info" class= "ch.qos.logback.classic.AsyncAppender">
+ <discardingThreshold >100</discardingThreshold>
+ <queueSize>1024</queueSize>
+ <appender-ref ref ="file_info"/>
+ </appender>
+
+ <appender name ="async_error" class= "ch.qos.logback.classic.AsyncAppender">
+ <discardingThreshold >100</discardingThreshold>
+ <queueSize>1024</queueSize>
+ <appender-ref ref ="file_error"/>
+ </appender>
+
+ <!-- SnailJob appender -->
+ <appender name="snail_log_server_appender" class="com.aizuda.snailjob.server.common.appender.SnailJobServerLogbackAppender">
+ </appender>
+
+ <!-- 鎺у埗鍙拌緭鍑烘棩蹇楃骇鍒� -->
+ <root level="info">
+ <appender-ref ref="console" />
+ <appender-ref ref="async_info" />
+ <appender-ref ref="async_error" />
+ <appender-ref ref="snail_log_server_appender" />
+ </root>
+</configuration>
diff --git a/ruoyi-modules/pom.xml b/ruoyi-modules/pom.xml
index 4044916..daff497 100644
--- a/ruoyi-modules/pom.xml
+++ b/ruoyi-modules/pom.xml
@@ -14,6 +14,7 @@
<module>ruoyi-generator</module>
<module>ruoyi-job</module>
<module>ruoyi-system</module>
+ <module>ruoyi-workflow</module>
</modules>
<artifactId>ruoyi-modules</artifactId>
diff --git a/ruoyi-modules/ruoyi-demo/src/main/java/org/dromara/demo/controller/SmsController.java b/ruoyi-modules/ruoyi-demo/src/main/java/org/dromara/demo/controller/SmsController.java
index fb19731..b993f60 100644
--- a/ruoyi-modules/ruoyi-demo/src/main/java/org/dromara/demo/controller/SmsController.java
+++ b/ruoyi-modules/ruoyi-demo/src/main/java/org/dromara/demo/controller/SmsController.java
@@ -5,7 +5,6 @@
import org.dromara.sms4j.api.SmsBlend;
import org.dromara.sms4j.api.entity.SmsResponse;
import org.dromara.sms4j.core.factory.SmsFactory;
-import org.dromara.sms4j.provider.enumerate.SupplierType;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
@@ -25,7 +24,6 @@
@RestController
@RequestMapping("/demo/sms")
public class SmsController {
-
/**
* 鍙戦�佺煭淇liyun
*
@@ -36,7 +34,7 @@
public R<Object> sendAliyun(String phones, String templateId) {
LinkedHashMap<String, String> map = new LinkedHashMap<>(1);
map.put("code", "1234");
- SmsBlend smsBlend = SmsFactory.createSmsBlend(SupplierType.ALIBABA);
+ SmsBlend smsBlend = SmsFactory.getSmsBlend("config1");
SmsResponse smsResponse = smsBlend.sendMessage(phones, templateId, map);
return R.ok(smsResponse);
}
@@ -52,9 +50,33 @@
LinkedHashMap<String, String> map = new LinkedHashMap<>(1);
// map.put("2", "娴嬭瘯娴嬭瘯");
map.put("1", "1234");
- SmsBlend smsBlend = SmsFactory.createSmsBlend(SupplierType.TENCENT);
+ SmsBlend smsBlend = SmsFactory.getSmsBlend("config2");
SmsResponse smsResponse = smsBlend.sendMessage(phones, templateId, map);
return R.ok(smsResponse);
}
+ /**
+ * 娣诲姞榛戝悕鍗�
+ *
+ * @param phone 鎵嬫満鍙�
+ */
+ @GetMapping("/addBlacklist")
+ public R<Object> addBlacklist(String phone){
+ SmsBlend smsBlend = SmsFactory.getSmsBlend("config1");
+ smsBlend.joinInBlacklist(phone);
+ return R.ok();
+ }
+
+ /**
+ * 绉婚櫎榛戝悕鍗�
+ *
+ * @param phone 鎵嬫満鍙�
+ */
+ @GetMapping("/removeBlacklist")
+ public R<Object> removeBlacklist(String phone){
+ SmsBlend smsBlend = SmsFactory.getSmsBlend("config1");
+ smsBlend.removeFromBlacklist(phone);
+ return R.ok();
+ }
+
}
diff --git a/ruoyi-modules/ruoyi-generator/src/main/java/org/dromara/generator/domain/GenTableColumn.java b/ruoyi-modules/ruoyi-generator/src/main/java/org/dromara/generator/domain/GenTableColumn.java
index 5ce7ad0..ebdb993 100644
--- a/ruoyi-modules/ruoyi-generator/src/main/java/org/dromara/generator/domain/GenTableColumn.java
+++ b/ruoyi-modules/ruoyi-generator/src/main/java/org/dromara/generator/domain/GenTableColumn.java
@@ -42,7 +42,7 @@
/**
* 鍒楁弿杩�
*/
- @TableField(updateStrategy = FieldStrategy.IGNORED, jdbcType = JdbcType.VARCHAR)
+ @TableField(updateStrategy = FieldStrategy.ALWAYS, jdbcType = JdbcType.VARCHAR)
private String columnComment;
/**
@@ -64,43 +64,43 @@
/**
* 鏄惁涓婚敭锛�1鏄級
*/
- @TableField(updateStrategy = FieldStrategy.IGNORED, jdbcType = JdbcType.VARCHAR)
+ @TableField(updateStrategy = FieldStrategy.ALWAYS, jdbcType = JdbcType.VARCHAR)
private String isPk;
/**
* 鏄惁鑷锛�1鏄級
*/
- @TableField(updateStrategy = FieldStrategy.IGNORED, jdbcType = JdbcType.VARCHAR)
+ @TableField(updateStrategy = FieldStrategy.ALWAYS, jdbcType = JdbcType.VARCHAR)
private String isIncrement;
/**
* 鏄惁蹇呭~锛�1鏄級
*/
- @TableField(updateStrategy = FieldStrategy.IGNORED, jdbcType = JdbcType.VARCHAR)
+ @TableField(updateStrategy = FieldStrategy.ALWAYS, jdbcType = JdbcType.VARCHAR)
private String isRequired;
/**
* 鏄惁涓烘彃鍏ュ瓧娈碉紙1鏄級
*/
- @TableField(updateStrategy = FieldStrategy.IGNORED, jdbcType = JdbcType.VARCHAR)
+ @TableField(updateStrategy = FieldStrategy.ALWAYS, jdbcType = JdbcType.VARCHAR)
private String isInsert;
/**
* 鏄惁缂栬緫瀛楁锛�1鏄級
*/
- @TableField(updateStrategy = FieldStrategy.IGNORED, jdbcType = JdbcType.VARCHAR)
+ @TableField(updateStrategy = FieldStrategy.ALWAYS, jdbcType = JdbcType.VARCHAR)
private String isEdit;
/**
* 鏄惁鍒楄〃瀛楁锛�1鏄級
*/
- @TableField(updateStrategy = FieldStrategy.IGNORED, jdbcType = JdbcType.VARCHAR)
+ @TableField(updateStrategy = FieldStrategy.ALWAYS, jdbcType = JdbcType.VARCHAR)
private String isList;
/**
* 鏄惁鏌ヨ瀛楁锛�1鏄級
*/
- @TableField(updateStrategy = FieldStrategy.IGNORED, jdbcType = JdbcType.VARCHAR)
+ @TableField(updateStrategy = FieldStrategy.ALWAYS, jdbcType = JdbcType.VARCHAR)
private String isQuery;
/**
diff --git a/ruoyi-modules/ruoyi-generator/src/main/resources/mapper/generator/GenTableMapper.xml b/ruoyi-modules/ruoyi-generator/src/main/resources/mapper/generator/GenTableMapper.xml
index b174589..901bbf0 100644
--- a/ruoyi-modules/ruoyi-generator/src/main/resources/mapper/generator/GenTableMapper.xml
+++ b/ruoyi-modules/ruoyi-generator/src/main/resources/mapper/generator/GenTableMapper.xml
@@ -19,7 +19,8 @@
select table_name, table_comment, create_time, update_time
from information_schema.tables
where table_schema = (select database())
- AND table_name NOT LIKE 'pj_%' AND table_name NOT LIKE 'gen_%'
+ AND table_name NOT LIKE 'sj_%' AND table_name NOT LIKE 'gen_%'
+ AND table_name NOT LIKE 'act_%' AND table_name NOT LIKE 'flw_%'
<if test="genTable.params.genTableNames != null and genTable.params.genTableNames.size > 0">
AND table_name NOT IN
<foreach collection="genTable.params.genTableNames" open="(" close=")" separator="," item="item">
@@ -40,7 +41,8 @@
where dt.table_name = dtc.table_name
and dt.table_name = uo.object_name
and uo.object_type = 'TABLE'
- AND dt.table_name NOT LIKE 'pj_%' AND dt.table_name NOT LIKE 'GEN_%'
+ AND dt.table_name NOT LIKE 'SJ_%' AND dt.table_name NOT LIKE 'GEN_%'
+ AND dt.table_name NOT LIKE 'ACT_%' AND dt.table_name NOT LIKE 'FLW_%'
<if test="genTable.params.genTableNames != null and genTable.params.genTableNames.size > 0">
AND lower(dt.table_name) NOT IN
<foreach collection="genTable.params.genTableNames" open="(" close=")" separator="," item="item">
@@ -69,7 +71,8 @@
AND n.nspname = 'public'::name
AND n.nspname <![CDATA[ <> ]]> ''::name
) list_table
- where table_name NOT LIKE 'pj_%' AND table_name NOT LIKE 'gen_%'
+ where table_name NOT LIKE 'sj_%' AND table_name NOT LIKE 'gen_%'
+ AND table_name NOT LIKE 'act_%' AND table_name NOT LIKE 'flw_%'
<if test="genTable.params.genTableNames != null and genTable.params.genTableNames.size > 0">
AND table_name NOT IN
<foreach collection="genTable.params.genTableNames" open="(" close=")" separator="," item="item">
@@ -92,7 +95,8 @@
FROM SYSOBJECTS D
INNER JOIN SYS.EXTENDED_PROPERTIES F ON D.ID = F.MAJOR_ID
AND F.MINOR_ID = 0 AND D.XTYPE = 'U' AND D.NAME != 'DTPROPERTIES'
- AND D.NAME NOT LIKE 'pj_%' AND D.NAME NOT LIKE 'gen_%'
+ AND D.NAME NOT LIKE 'sj_%' AND D.NAME NOT LIKE 'gen_%'
+ AND D.NAME NOT LIKE 'act_%' AND D.NAME NOT LIKE 'flw_%'
<if test="genTable.params.genTableNames != null and genTable.params.genTableNames.size > 0">
AND D.NAME NOT IN
<foreach collection="genTable.params.genTableNames" open="(" close=")" separator="," item="item">
@@ -112,7 +116,9 @@
<select id="selectDbTableListByNames" resultMap="GenTableResult">
<if test="@org.dromara.common.mybatis.helper.DataBaseHelper@isMySql()">
select table_name, table_comment, create_time, update_time from information_schema.tables
- where table_name NOT LIKE 'pj_%' and table_name NOT LIKE 'gen_%' and table_schema = (select database())
+ where table_schema = (select database())
+ and table_name NOT LIKE 'sj_%' and table_name NOT LIKE 'gen_%'
+ and table_name NOT LIKE 'act_%' AND table_name NOT LIKE 'flw_%'
and table_name in
<foreach collection="array" item="name" open="(" separator="," close=")">
#{name}
@@ -124,7 +130,8 @@
where dt.table_name = dtc.table_name
and dt.table_name = uo.object_name
and uo.object_type = 'TABLE'
- AND dt.table_name NOT LIKE 'pj_%' AND dt.table_name NOT LIKE 'GEN_%'
+ and dt.table_name NOT LIKE 'SJ_%' AND dt.table_name NOT LIKE 'GEN_%'
+ and dt.table_name NOT LIKE 'ACT_%' AND dt.table_name NOT LIKE 'FLW_%'
and lower(dt.table_name) in
<foreach collection="array" item="name" open="(" separator="," close=")">
#{name}
@@ -144,7 +151,8 @@
AND n.nspname = 'public'::name
AND n.nspname <![CDATA[ <> ]]> ''::name
) list_table
- where table_name NOT LIKE 'pj_%' and table_name NOT LIKE 'gen_%'
+ where table_name NOT LIKE 'sj_%' and table_name NOT LIKE 'gen_%'
+ and table_name NOT LIKE 'act_%' and table_name NOT LIKE 'flw_%'
and table_name in
<foreach collection="array" item="name" open="(" separator="," close=")">
#{name}
@@ -158,7 +166,8 @@
FROM SYSOBJECTS D
INNER JOIN SYS.EXTENDED_PROPERTIES F ON D.ID = F.MAJOR_ID
AND F.MINOR_ID = 0 AND D.XTYPE = 'U' AND D.NAME != 'DTPROPERTIES'
- AND D.NAME NOT LIKE 'pj_%' AND D.NAME NOT LIKE 'gen_%'
+ AND D.NAME NOT LIKE 'sj_%' AND D.NAME NOT LIKE 'gen_%'
+ AND D.NAME NOT LIKE 'act_%' AND D.NAME NOT LIKE 'flw_%'
AND D.NAME in
<foreach collection="array" item="name" open="(" separator="," close=")">
#{name}
@@ -169,7 +178,9 @@
<select id="selectTableByName" parameterType="String" resultMap="GenTableResult">
<if test="@org.dromara.common.mybatis.helper.DataBaseHelper@isMySql()">
select table_name, table_comment, create_time, update_time from information_schema.tables
- where table_name NOT LIKE 'pj_%' and table_name NOT LIKE 'gen_%' and table_schema = (select database())
+ where table_schema = (select database())
+ and table_name NOT LIKE 'sj_%' and table_name NOT LIKE 'gen_%'
+ and table_name NOT LIKE 'act_%' AND table_name NOT LIKE 'flw_%'
and table_name = #{tableName}
</if>
<if test="@org.dromara.common.mybatis.helper.DataBaseHelper@isOracle()">
@@ -178,7 +189,8 @@
where dt.table_name = dtc.table_name
and dt.table_name = uo.object_name
and uo.object_type = 'TABLE'
- AND dt.table_name NOT LIKE 'pj_%' AND dt.table_name NOT LIKE 'GEN_%'
+ AND dt.table_name NOT LIKE 'SJ_%' AND dt.table_name NOT LIKE 'GEN_%'
+ AND dt.table_name NOT LIKE 'ACT_%' AND dt.table_name NOT LIKE 'FLW_%'
AND dt.table_name NOT IN (select table_name from gen_table)
and lower(dt.table_name) = #{tableName}
</if>
@@ -196,7 +208,8 @@
AND n.nspname = 'public'::name
AND n.nspname <![CDATA[ <> ]]> ''::name
) list_table
- where table_name NOT LIKE 'pj_%' and table_name NOT LIKE 'gen_%'
+ where table_name NOT LIKE 'sj_%' and table_name NOT LIKE 'gen_%'
+ and table_name NOT LIKE 'act_%' and table_name NOT LIKE 'flw_%'
and table_name = #{tableName}
</if>
<if test="@org.dromara.common.mybatis.helper.DataBaseHelper@isSqlServer()">
@@ -207,7 +220,8 @@
FROM SYSOBJECTS D
INNER JOIN SYS.EXTENDED_PROPERTIES F ON D.ID = F.MAJOR_ID
AND F.MINOR_ID = 0 AND D.XTYPE = 'U' AND D.NAME != 'DTPROPERTIES'
- AND D.NAME NOT LIKE 'pj_%' AND D.NAME NOT LIKE 'gen_%'
+ AND D.NAME NOT LIKE 'sj_%' AND D.NAME NOT LIKE 'gen_%'
+ AND D.NAME NOT LIKE 'act_%' AND D.NAME NOT LIKE 'flw_%'
AND D.NAME = #{tableName}
</if>
</select>
diff --git a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/controller.java.vm b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/controller.java.vm
index 14177b5..6438971 100644
--- a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/controller.java.vm
+++ b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/controller.java.vm
@@ -20,7 +20,7 @@
import ${packageName}.domain.vo.${ClassName}Vo;
import ${packageName}.domain.bo.${ClassName}Bo;
import ${packageName}.service.I${ClassName}Service;
-#if($table.crud || $table.sub)
+#if($table.crud)
import org.dromara.common.mybatis.core.page.TableDataInfo;
#elseif($table.tree)
#end
@@ -44,7 +44,7 @@
*/
@SaCheckPermission("${permissionPrefix}:list")
@GetMapping("/list")
-#if($table.crud || $table.sub)
+#if($table.crud)
public TableDataInfo<${ClassName}Vo> list(${ClassName}Bo bo, PageQuery pageQuery) {
return ${className}Service.queryPageList(bo, pageQuery);
}
diff --git a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/service.java.vm b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/service.java.vm
index d596a0e..4db9030 100644
--- a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/service.java.vm
+++ b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/service.java.vm
@@ -1,9 +1,8 @@
package ${packageName}.service;
-import ${packageName}.domain.${ClassName};
import ${packageName}.domain.vo.${ClassName}Vo;
import ${packageName}.domain.bo.${ClassName}Bo;
-#if($table.crud || $table.sub)
+#if($table.crud)
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.mybatis.core.page.PageQuery;
#end
@@ -21,33 +20,53 @@
/**
* 鏌ヨ${functionName}
+ *
+ * @param ${pkColumn.javaField} 涓婚敭
+ * @return ${functionName}
*/
${ClassName}Vo queryById(${pkColumn.javaType} ${pkColumn.javaField});
-#if($table.crud || $table.sub)
+#if($table.crud)
/**
- * 鏌ヨ${functionName}鍒楄〃
+ * 鍒嗛〉鏌ヨ${functionName}鍒楄〃
+ *
+ * @param bo 鏌ヨ鏉′欢
+ * @param pageQuery 鍒嗛〉鍙傛暟
+ * @return ${functionName}鍒嗛〉鍒楄〃
*/
TableDataInfo<${ClassName}Vo> queryPageList(${ClassName}Bo bo, PageQuery pageQuery);
#end
/**
- * 鏌ヨ${functionName}鍒楄〃
+ * 鏌ヨ绗﹀悎鏉′欢鐨�${functionName}鍒楄〃
+ *
+ * @param bo 鏌ヨ鏉′欢
+ * @return ${functionName}鍒楄〃
*/
List<${ClassName}Vo> queryList(${ClassName}Bo bo);
/**
* 鏂板${functionName}
+ *
+ * @param bo ${functionName}
+ * @return 鏄惁鏂板鎴愬姛
*/
Boolean insertByBo(${ClassName}Bo bo);
/**
* 淇敼${functionName}
+ *
+ * @param bo ${functionName}
+ * @return 鏄惁淇敼鎴愬姛
*/
Boolean updateByBo(${ClassName}Bo bo);
/**
* 鏍¢獙骞舵壒閲忓垹闄�${functionName}淇℃伅
+ *
+ * @param ids 寰呭垹闄ょ殑涓婚敭闆嗗悎
+ * @param isValid 鏄惁杩涜鏈夋晥鎬ф牎楠�
+ * @return 鏄惁鍒犻櫎鎴愬姛
*/
Boolean deleteWithValidByIds(Collection<${pkColumn.javaType}> ids, Boolean isValid);
}
diff --git a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/serviceImpl.java.vm b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/serviceImpl.java.vm
index 75a9b83..e7236fd 100644
--- a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/serviceImpl.java.vm
+++ b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/java/serviceImpl.java.vm
@@ -2,7 +2,7 @@
import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.common.core.utils.StringUtils;
-#if($table.crud || $table.sub)
+#if($table.crud)
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.mybatis.core.page.PageQuery;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
@@ -35,15 +35,22 @@
/**
* 鏌ヨ${functionName}
+ *
+ * @param ${pkColumn.javaField} 涓婚敭
+ * @return ${functionName}
*/
@Override
public ${ClassName}Vo queryById(${pkColumn.javaType} ${pkColumn.javaField}){
return baseMapper.selectVoById(${pkColumn.javaField});
}
-#if($table.crud || $table.sub)
+#if($table.crud)
/**
- * 鏌ヨ${functionName}鍒楄〃
+ * 鍒嗛〉鏌ヨ${functionName}鍒楄〃
+ *
+ * @param bo 鏌ヨ鏉′欢
+ * @param pageQuery 鍒嗛〉鍙傛暟
+ * @return ${functionName}鍒嗛〉鍒楄〃
*/
@Override
public TableDataInfo<${ClassName}Vo> queryPageList(${ClassName}Bo bo, PageQuery pageQuery) {
@@ -54,7 +61,10 @@
#end
/**
- * 鏌ヨ${functionName}鍒楄〃
+ * 鏌ヨ绗﹀悎鏉′欢鐨�${functionName}鍒楄〃
+ *
+ * @param bo 鏌ヨ鏉′欢
+ * @return ${functionName}鍒楄〃
*/
@Override
public List<${ClassName}Vo> queryList(${ClassName}Bo bo) {
@@ -91,6 +101,9 @@
/**
* 鏂板${functionName}
+ *
+ * @param bo ${functionName}
+ * @return 鏄惁鏂板鎴愬姛
*/
@Override
public Boolean insertByBo(${ClassName}Bo bo) {
@@ -106,6 +119,9 @@
/**
* 淇敼${functionName}
+ *
+ * @param bo ${functionName}
+ * @return 鏄惁淇敼鎴愬姛
*/
@Override
public Boolean updateByBo(${ClassName}Bo bo) {
@@ -122,7 +138,11 @@
}
/**
- * 鎵归噺鍒犻櫎${functionName}
+ * 鏍¢獙骞舵壒閲忓垹闄�${functionName}淇℃伅
+ *
+ * @param ids 寰呭垹闄ょ殑涓婚敭闆嗗悎
+ * @param isValid 鏄惁杩涜鏈夋晥鎬ф牎楠�
+ * @return 鏄惁鍒犻櫎鎴愬姛
*/
@Override
public Boolean deleteWithValidByIds(Collection<${pkColumn.javaType}> ids, Boolean isValid) {
diff --git a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index-tree.vue.vm b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index-tree.vue.vm
index af3275e..d13ef2f 100644
--- a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index-tree.vue.vm
+++ b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index-tree.vue.vm
@@ -1,8 +1,9 @@
<template>
<div class="p-2">
<transition :enter-active-class="proxy?.animate.searchAnimate.enter" :leave-active-class="proxy?.animate.searchAnimate.leave">
- <div class="search" v-show="showSearch">
- <el-form :model="queryParams" ref="queryFormRef" :inline="true" label-width="68px">
+ <div v-show="showSearch" class="mb-[10px]">
+ <el-card shadow="hover">
+ <el-form ref="queryFormRef" :model="queryParams" :inline="true">
#foreach($column in $columns)
#if($column.query)
#set($dictType=$column.dictType)
@@ -14,38 +15,33 @@
#set($comment=$column.columnComment)
#end
#if($column.htmlType == "input" || $column.htmlType == "textarea")
- <el-form-item label="${comment}" prop="${column.javaField}">
- <el-input v-model="queryParams.${column.javaField}" placeholder="璇疯緭鍏�${comment}" clearable style="width: 240px" @keyup.enter="handleQuery" />
- </el-form-item>
+ <el-form-item label="${comment}" prop="${column.javaField}">
+ <el-input v-model="queryParams.${column.javaField}" placeholder="璇疯緭鍏�${comment}" clearable @keyup.enter="handleQuery" />
+ </el-form-item>
#elseif(($column.htmlType == "select" || $column.htmlType == "radio") && "" != $dictType)
- <el-form-item label="${comment}" prop="${column.javaField}">
- <el-select v-model="queryParams.${column.javaField}" placeholder="璇烽�夋嫨${comment}" clearable>
- <el-option
- v-for="dict in ${dictType}"
- :key="dict.value"
- :label="dict.label"
- :value="dict.value"
- />
- </el-select>
- </el-form-item>
+ <el-form-item label="${comment}" prop="${column.javaField}">
+ <el-select v-model="queryParams.${column.javaField}" placeholder="璇烽�夋嫨${comment}" clearable>
+ <el-option v-for="dict in ${dictType}" :key="dict.value" :label="dict.label" :value="dict.value"/>
+ </el-select>
+ </el-form-item>
#elseif(($column.htmlType == "select" || $column.htmlType == "radio") && $dictType)
- <el-form-item label="${comment}" prop="${column.javaField}">
- <el-select v-model="queryParams.${column.javaField}" placeholder="璇烽�夋嫨${comment}" clearable>
- <el-option label="璇烽�夋嫨瀛楀吀鐢熸垚" value="" />
- </el-select>
- </el-form-item>
+ <el-form-item label="${comment}" prop="${column.javaField}">
+ <el-select v-model="queryParams.${column.javaField}" placeholder="璇烽�夋嫨${comment}" clearable>
+ <el-option label="璇烽�夋嫨瀛楀吀鐢熸垚" value="" />
+ </el-select>
+ </el-form-item>
#elseif($column.htmlType == "datetime" && $column.queryType != "BETWEEN")
- <el-form-item label="${comment}" prop="${column.javaField}">
- <el-date-picker clearable
+ <el-form-item label="${comment}" prop="${column.javaField}">
+ <el-date-picker clearable
v-model="queryParams.${column.javaField}"
type="date"
value-format="YYYY-MM-DD"
placeholder="閫夋嫨${comment}"
- />
- </el-form-item>
+ />
+ </el-form-item>
#elseif($column.htmlType == "datetime" && $column.queryType == "BETWEEN")
- <el-form-item label="${comment}" style="width: 308px">
- <el-date-picker
+ <el-form-item label="${comment}" style="width: 308px">
+ <el-date-picker
v-model="dateRange${AttrName}"
value-format="YYYY-MM-DD HH:mm:ss"
type="daterange"
@@ -53,16 +49,17 @@
start-placeholder="寮�濮嬫棩鏈�"
end-placeholder="缁撴潫鏃ユ湡"
:default-time="[new Date(2000, 1, 1, 0, 0, 0), new Date(2000, 1, 1, 23, 59, 59)]"
- />
- </el-form-item>
+ />
+ </el-form-item>
#end
#end
#end
- <el-form-item>
- <el-button type="primary" icon="Search" @click="handleQuery">鎼滅储</el-button>
- <el-button icon="Refresh" @click="resetQuery">閲嶇疆</el-button>
- </el-form-item>
- </el-form>
+ <el-form-item>
+ <el-button type="primary" icon="Search" @click="handleQuery">鎼滅储</el-button>
+ <el-button icon="Refresh" @click="resetQuery">閲嶇疆</el-button>
+ </el-form-item>
+ </el-form>
+ </el-card>
</div>
</transition>
@@ -79,12 +76,12 @@
</el-row>
</template>
<el-table
+ ref="${businessName}TableRef"
v-loading="loading"
:data="${businessName}List"
row-key="${treeCode}"
:default-expand-all="isExpandAll"
- :tree-props="{children: 'children', hasChildren: 'hasChildren'}"
- ref="${businessName}TableRef"
+ :tree-props="{ children: 'children', hasChildren: 'hasChildren' }"
>
#foreach($column in $columns)
#set($javaField=$column.javaField)
@@ -225,9 +222,9 @@
v-for="dict in ${dictType}"
:key="dict.value"
#if($column.javaType == "Integer" || $column.javaType == "Long")
- :label="parseInt(dict.value)"
+ :value="parseInt(dict.value)"
#else
- :label="dict.value"
+ :value="dict.value"
#end
>{{dict.label}}</el-radio>
</el-radio-group>
@@ -235,7 +232,7 @@
#elseif($column.htmlType == "radio" && $dictType)
<el-form-item label="${comment}" prop="${field}">
<el-radio-group v-model="form.${field}">
- <el-radio label="1">璇烽�夋嫨瀛楀吀鐢熸垚</el-radio>
+ <el-radio value="1">璇烽�夋嫨瀛楀吀鐢熸垚</el-radio>
</el-radio-group>
</el-form-item>
#elseif($column.htmlType == "datetime")
@@ -424,9 +421,9 @@
reset();
getTreeselect();
if (row != null && row.${treeCode}) {
- form.value.${treeParentCode} = row.${treeCode};
+ form.value.${treeParentCode} = row.${treeCode};
} else {
- form.value.${treeParentCode} = 0;
+ form.value.${treeParentCode} = 0;
}
dialog.visible = true;
dialog.title = "娣诲姞${functionName}";
diff --git a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index.vue.vm b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index.vue.vm
index 8b132f4..886f4ab 100644
--- a/ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index.vue.vm
+++ b/ruoyi-modules/ruoyi-generator/src/main/resources/vm/vue/index.vue.vm
@@ -1,8 +1,9 @@
<template>
<div class="p-2">
<transition :enter-active-class="proxy?.animate.searchAnimate.enter" :leave-active-class="proxy?.animate.searchAnimate.leave">
- <div class="search" v-show="showSearch">
- <el-form :model="queryParams" ref="queryFormRef" :inline="true" label-width="68px">
+ <div v-show="showSearch" class="mb-[10px]">
+ <el-card shadow="hover">
+ <el-form ref="queryFormRef" :model="queryParams" :inline="true">
#foreach($column in $columns)
#if($column.query)
#set($dictType=$column.dictType)
@@ -14,38 +15,33 @@
#set($comment=$column.columnComment)
#end
#if($column.htmlType == "input" || $column.htmlType == "textarea")
- <el-form-item label="${comment}" prop="${column.javaField}">
- <el-input v-model="queryParams.${column.javaField}" placeholder="璇疯緭鍏�${comment}" clearable style="width: 240px" @keyup.enter="handleQuery" />
- </el-form-item>
+ <el-form-item label="${comment}" prop="${column.javaField}">
+ <el-input v-model="queryParams.${column.javaField}" placeholder="璇疯緭鍏�${comment}" clearable @keyup.enter="handleQuery" />
+ </el-form-item>
#elseif(($column.htmlType == "select" || $column.htmlType == "radio") && "" != $dictType)
- <el-form-item label="${comment}" prop="${column.javaField}">
- <el-select v-model="queryParams.${column.javaField}" placeholder="璇烽�夋嫨${comment}" clearable>
- <el-option
- v-for="dict in ${dictType}"
- :key="dict.value"
- :label="dict.label"
- :value="dict.value"
- />
- </el-select>
- </el-form-item>
+ <el-form-item label="${comment}" prop="${column.javaField}">
+ <el-select v-model="queryParams.${column.javaField}" placeholder="璇烽�夋嫨${comment}" clearable >
+ <el-option v-for="dict in ${dictType}" :key="dict.value" :label="dict.label" :value="dict.value"/>
+ </el-select>
+ </el-form-item>
#elseif(($column.htmlType == "select" || $column.htmlType == "radio") && $dictType)
- <el-form-item label="${comment}" prop="${column.javaField}">
- <el-select v-model="queryParams.${column.javaField}" placeholder="璇烽�夋嫨${comment}" clearable>
- <el-option label="璇烽�夋嫨瀛楀吀鐢熸垚" value="" />
- </el-select>
- </el-form-item>
+ <el-form-item label="${comment}" prop="${column.javaField}">
+ <el-select v-model="queryParams.${column.javaField}" placeholder="璇烽�夋嫨${comment}" clearable >
+ <el-option label="璇烽�夋嫨瀛楀吀鐢熸垚" value="" />
+ </el-select>
+ </el-form-item>
#elseif($column.htmlType == "datetime" && $column.queryType != "BETWEEN")
- <el-form-item label="${comment}" prop="${column.javaField}">
- <el-date-picker clearable
- v-model="queryParams.${column.javaField}"
- type="date"
- value-format="YYYY-MM-DD"
- placeholder="璇烽�夋嫨${comment}"
- />
- </el-form-item>
+ <el-form-item label="${comment}" prop="${column.javaField}">
+ <el-date-picker clearable
+ v-model="queryParams.${column.javaField}"
+ type="date"
+ value-format="YYYY-MM-DD"
+ placeholder="璇烽�夋嫨${comment}"
+ />
+ </el-form-item>
#elseif($column.htmlType == "datetime" && $column.queryType == "BETWEEN")
- <el-form-item label="${comment}" style="width: 308px">
- <el-date-picker
+ <el-form-item label="${comment}" style="width: 308px">
+ <el-date-picker
v-model="dateRange${AttrName}"
value-format="YYYY-MM-DD HH:mm:ss"
type="daterange"
@@ -53,16 +49,17 @@
start-placeholder="寮�濮嬫棩鏈�"
end-placeholder="缁撴潫鏃ユ湡"
:default-time="[new Date(2000, 1, 1, 0, 0, 0), new Date(2000, 1, 1, 23, 59, 59)]"
- />
- </el-form-item>
+ />
+ </el-form-item>
#end
#end
#end
- <el-form-item>
- <el-button type="primary" icon="Search" @click="handleQuery">鎼滅储</el-button>
- <el-button icon="Refresh" @click="resetQuery">閲嶇疆</el-button>
- </el-form-item>
- </el-form>
+ <el-form-item>
+ <el-button type="primary" icon="Search" @click="handleQuery">鎼滅储</el-button>
+ <el-button icon="Refresh" @click="resetQuery">閲嶇疆</el-button>
+ </el-form-item>
+ </el-form>
+ </el-card>
</div>
</transition>
@@ -135,13 +132,7 @@
</el-table-column>
</el-table>
- <pagination
- v-show="total>0"
- :total="total"
- v-model:page="queryParams.pageNum"
- v-model:limit="queryParams.pageSize"
- @pagination="getList"
- />
+ <pagination v-show="total > 0" :total="total" v-model:page="queryParams.pageNum" v-model:limit="queryParams.pageSize" @pagination="getList" />
</el-card>
<!-- 娣诲姞鎴栦慨鏀�${functionName}瀵硅瘽妗� -->
<el-dialog :title="dialog.title" v-model="dialog.visible" width="500px" append-to-body>
@@ -214,12 +205,12 @@
<el-form-item label="${comment}" prop="${field}">
<el-radio-group v-model="form.${field}">
<el-radio
- v-for="dict in ${dictType}"
- :key="dict.value"
+ v-for="dict in ${dictType}"
+ :key="dict.value"
#if($column.javaType == "Integer" || $column.javaType == "Long")
- :label="parseInt(dict.value)"
+ :value="parseInt(dict.value)"
#else
- :label="dict.value"
+ :value="dict.value"
#end
>{{dict.label}}</el-radio>
</el-radio-group>
@@ -227,7 +218,7 @@
#elseif($column.htmlType == "radio" && $dictType)
<el-form-item label="${comment}" prop="${field}">
<el-radio-group v-model="form.${field}">
- <el-radio label="1">璇烽�夋嫨瀛楀吀鐢熸垚</el-radio>
+ <el-radio value="1">璇烽�夋嫨瀛楀吀鐢熸垚</el-radio>
</el-radio-group>
</el-form-item>
#elseif($column.htmlType == "datetime")
@@ -439,7 +430,7 @@
} else {
await add${BusinessName}(form.value).finally(() => buttonLoading.value = false);
}
- proxy?.#[[$modal]]#.msgSuccess("淇敼鎴愬姛");
+ proxy?.#[[$modal]]#.msgSuccess("鎿嶄綔鎴愬姛");
dialog.visible = false;
await getList();
}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/package-info.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/package-info.java
index 325abdd..2f118b0 100644
--- a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/package-info.java
+++ b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/package-info.java
@@ -1,6 +1 @@
-/**
- * 婕旂ず鐢ㄤ緥
- * copy from https://github.com/PowerJob/PowerJob/tree/master/powerjob-worker-samples/src/main/java/tech/powerjob/samples
- */
-
package org.dromara.job;
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/BroadcastProcessorDemo.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/BroadcastProcessorDemo.java
deleted file mode 100644
index 2b4c28a..0000000
--- a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/BroadcastProcessorDemo.java
+++ /dev/null
@@ -1,56 +0,0 @@
-package org.dromara.job.processors;
-
-import lombok.extern.slf4j.Slf4j;
-import org.springframework.stereotype.Component;
-import tech.powerjob.common.utils.NetUtils;
-import tech.powerjob.worker.core.processor.ProcessResult;
-import tech.powerjob.worker.core.processor.TaskContext;
-import tech.powerjob.worker.core.processor.TaskResult;
-import tech.powerjob.worker.core.processor.sdk.BroadcastProcessor;
-import tech.powerjob.worker.log.OmsLogger;
-
-import java.util.List;
-
-/**
- * 骞挎挱澶勭悊鍣� 绀轰緥
- *
- * @author tjq
- * @since 2020/4/17
- */
-@Slf4j
-@Component
-public class BroadcastProcessorDemo implements BroadcastProcessor {
-
- @Override
- public ProcessResult preProcess(TaskContext context) {
- System.out.println("===== BroadcastProcessorDemo#preProcess ======");
- context.getOmsLogger().info("BroadcastProcessorDemo#preProcess, current host: {}", NetUtils.getLocalHost());
- if ("rootFailed".equals(context.getJobParams())) {
- return new ProcessResult(false, "console need failed");
- } else {
- return new ProcessResult(true);
- }
- }
-
- @Override
- public ProcessResult process(TaskContext taskContext) throws Exception {
- OmsLogger logger = taskContext.getOmsLogger();
- System.out.println("===== BroadcastProcessorDemo#process ======");
- logger.info("BroadcastProcessorDemo#process, current host: {}", NetUtils.getLocalHost());
- long sleepTime = 1000;
- try {
- sleepTime = Long.parseLong(taskContext.getJobParams());
- } catch (Exception e) {
- logger.warn("[BroadcastProcessor] parse sleep time failed!", e);
- }
- Thread.sleep(Math.max(sleepTime, 1000));
- return new ProcessResult(true);
- }
-
- @Override
- public ProcessResult postProcess(TaskContext context, List<TaskResult> taskResults) {
- System.out.println("===== BroadcastProcessorDemo#postProcess ======");
- context.getOmsLogger().info("BroadcastProcessorDemo#postProcess, current host: {}, taskResult: {}", NetUtils.getLocalHost(), taskResults);
- return new ProcessResult(true, "success");
- }
-}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/LogTestProcessor.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/LogTestProcessor.java
deleted file mode 100644
index 2a1000f..0000000
--- a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/LogTestProcessor.java
+++ /dev/null
@@ -1,41 +0,0 @@
-package org.dromara.job.processors;
-
-import com.alibaba.fastjson.JSONObject;
-import org.springframework.stereotype.Component;
-import tech.powerjob.official.processors.util.CommonUtils;
-import tech.powerjob.worker.core.processor.ProcessResult;
-import tech.powerjob.worker.core.processor.TaskContext;
-import tech.powerjob.worker.core.processor.sdk.BasicProcessor;
-import tech.powerjob.worker.log.OmsLogger;
-
-import java.util.Date;
-import java.util.Optional;
-
-/**
- * LogTestProcessor
- *
- * @author tjq
- * @since 2022/9/18
- */
-@Component
-public class LogTestProcessor implements BasicProcessor {
-
- @Override
- public ProcessResult process(TaskContext context) throws Exception {
-
- final OmsLogger omsLogger = context.getOmsLogger();
- final String parseParams = CommonUtils.parseParams(context);
- final JSONObject config = Optional.ofNullable(JSONObject.parseObject(parseParams)).orElse(new JSONObject());
-
- final long loopTimes = Optional.ofNullable(config.getLong("loopTimes")).orElse(1000L);
-
- for (int i = 0; i < loopTimes; i++) {
- omsLogger.debug("[DEBUG] one DEBUG log in {}", new Date());
- omsLogger.info("[INFO] one INFO log in {}", new Date());
- omsLogger.warn("[WARN] one WARN log in {}", new Date());
- omsLogger.error("[ERROR] one ERROR log in {}", new Date());
- }
-
- return new ProcessResult(true);
- }
-}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/MapProcessorDemo.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/MapProcessorDemo.java
deleted file mode 100644
index 720d333..0000000
--- a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/MapProcessorDemo.java
+++ /dev/null
@@ -1,93 +0,0 @@
-package org.dromara.job.processors;
-
-import com.google.common.collect.Lists;
-import lombok.AllArgsConstructor;
-import lombok.Getter;
-import lombok.NoArgsConstructor;
-import org.dromara.common.json.utils.JsonUtils;
-import org.springframework.stereotype.Component;
-import tech.powerjob.worker.core.processor.ProcessResult;
-import tech.powerjob.worker.core.processor.TaskContext;
-import tech.powerjob.worker.core.processor.sdk.MapProcessor;
-
-import java.util.List;
-import java.util.concurrent.ThreadLocalRandom;
-
-/**
- * Map澶勭悊鍣� 绀轰緥
- *
- * @author tjq
- * @since 2020/4/18
- */
-@Component
-public class MapProcessorDemo implements MapProcessor {
-
-
- /**
- * 姣忎竴鎵瑰彂閫佷换鍔″ぇ灏�
- */
- private static final int BATCH_SIZE = 100;
- /**
- * 鍙戦�佺殑鎵规
- */
- private static final int BATCH_NUM = 5;
-
- @Override
- public ProcessResult process(TaskContext context) throws Exception {
-
- log.info("============== MapProcessorDemo#process ==============");
- log.info("isRootTask:{}", isRootTask());
- log.info("taskContext:{}", JsonUtils.toJsonString(context));
-
- if (isRootTask()) {
- log.info("==== MAP ====");
- List<SubTask> subTasks = Lists.newLinkedList();
- for (int j = 0; j < BATCH_NUM; j++) {
- SubTask subTask = new SubTask();
- subTask.siteId = j;
- subTask.itemIds = Lists.newLinkedList();
- subTasks.add(subTask);
- for (int i = 0; i < BATCH_SIZE; i++) {
- subTask.itemIds.add(i + j * 100);
- }
- }
- map(subTasks, "MAP_TEST_TASK");
- return new ProcessResult(true, "map successfully");
- } else {
-
- log.info("==== PROCESS ====");
- SubTask subTask = (SubTask) context.getSubTask();
- for (Integer itemId : subTask.getItemIds()) {
- if (Thread.interrupted()) {
- // 浠诲姟琚腑鏂�
- log.info("job has been stop! so stop to process subTask: {} => {}", subTask.getSiteId(), itemId);
- break;
- }
- log.info("processing subTask: {} => {}", subTask.getSiteId(), itemId);
- int max = Integer.MAX_VALUE >> 7;
- for (int i = 0; ; i++) {
- // 妯℃嫙鑰楁椂鎿嶄綔
- if (i > max) {
- break;
- }
- }
- }
- // 娴嬭瘯鍦� Map 浠诲姟涓拷鍔犱笂涓嬫枃
- context.getWorkflowContext().appendData2WfContext("Yasuo", "A sword's poor company for a long road.");
- boolean b = ThreadLocalRandom.current().nextBoolean();
- if (context.getCurrentRetryTimes() >= 1) {
- // 閲嶈瘯鐨勮瘽涓�瀹氫細鎴愬姛
- b = true;
- }
- return new ProcessResult(b, "RESULT:" + b);
- }
- }
-
- @Getter
- @NoArgsConstructor
- @AllArgsConstructor
- public static class SubTask {
- private Integer siteId;
- private List<Integer> itemIds;
- }
-}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/MapReduceProcessorDemo.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/MapReduceProcessorDemo.java
deleted file mode 100644
index 1498854..0000000
--- a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/MapReduceProcessorDemo.java
+++ /dev/null
@@ -1,93 +0,0 @@
-package org.dromara.job.processors;
-
-import cn.hutool.core.lang.Dict;
-import com.google.common.collect.Lists;
-import lombok.AllArgsConstructor;
-import lombok.Getter;
-import lombok.NoArgsConstructor;
-import lombok.ToString;
-import lombok.extern.slf4j.Slf4j;
-import org.dromara.common.json.utils.JsonUtils;
-import org.springframework.stereotype.Component;
-import tech.powerjob.worker.core.processor.ProcessResult;
-import tech.powerjob.worker.core.processor.TaskContext;
-import tech.powerjob.worker.core.processor.TaskResult;
-import tech.powerjob.worker.core.processor.sdk.MapReduceProcessor;
-import tech.powerjob.worker.log.OmsLogger;
-
-import java.util.List;
-import java.util.concurrent.ThreadLocalRandom;
-
-/**
- * MapReduce 澶勭悊鍣ㄧず渚�
- * 鎺у埗鍙板弬鏁帮細{"batchSize": 100, "batchNum": 2}
- *
- * @author tjq
- * @since 2020/4/17
- */
-@Slf4j
-@Component
-public class MapReduceProcessorDemo implements MapReduceProcessor {
-
- @Override
- public ProcessResult process(TaskContext context) throws Exception {
-
- OmsLogger omsLogger = context.getOmsLogger();
-
- log.info("============== TestMapReduceProcessor#process ==============");
- log.info("isRootTask:{}", isRootTask());
- log.info("taskContext:{}", JsonUtils.toJsonString(context));
-
- // 鏍规嵁鎺у埗鍙板弬鏁拌幏鍙朚R鎵规鍙婂瓙浠诲姟澶у皬
- final Dict jobParams = JsonUtils.parseMap(context.getJobParams());
-
- Integer batchSize = (Integer) jobParams.getOrDefault("batchSize", 100);
- Integer batchNum = (Integer) jobParams.getOrDefault("batchNum", 10);
-
- if (isRootTask()) {
- log.info("==== MAP ====");
- omsLogger.info("[DemoMRProcessor] start root task~");
- List<TestSubTask> subTasks = Lists.newLinkedList();
- for (int j = 0; j < batchNum; j++) {
- for (int i = 0; i < batchSize; i++) {
- int x = j * batchSize + i;
- subTasks.add(new TestSubTask("name" + x, x));
- }
- map(subTasks, "MAP_TEST_TASK");
- subTasks.clear();
- }
- omsLogger.info("[DemoMRProcessor] map success~");
- return new ProcessResult(true, "MAP_SUCCESS");
- } else {
- log.info("==== NORMAL_PROCESS ====");
- omsLogger.info("[DemoMRProcessor] process subTask: {}.", JsonUtils.toJsonString(context.getSubTask()));
- log.info("subTask: {}", JsonUtils.toJsonString(context.getSubTask()));
- Thread.sleep(1000);
- if (context.getCurrentRetryTimes() == 0) {
- return new ProcessResult(false, "FIRST_FAILED");
- } else {
- return new ProcessResult(true, "PROCESS_SUCCESS");
- }
- }
- }
-
- @Override
- public ProcessResult reduce(TaskContext context, List<TaskResult> taskResults) {
- log.info("================ MapReduceProcessorDemo#reduce ================");
- log.info("TaskContext: {}", JsonUtils.toJsonString(context));
- log.info("List<TaskResult>: {}", JsonUtils.toJsonString(taskResults));
- context.getOmsLogger().info("MapReduce job finished, result is {}.", taskResults);
-
- boolean success = ThreadLocalRandom.current().nextBoolean();
- return new ProcessResult(success, context + ": " + success);
- }
-
- @Getter
- @ToString
- @NoArgsConstructor
- @AllArgsConstructor
- public static class TestSubTask {
- private String name;
- private int age;
- }
-}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/SimpleProcessor.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/SimpleProcessor.java
deleted file mode 100644
index 3342cfe..0000000
--- a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/SimpleProcessor.java
+++ /dev/null
@@ -1,35 +0,0 @@
-package org.dromara.job.processors;
-
-import org.springframework.stereotype.Component;
-import tech.powerjob.worker.core.processor.ProcessResult;
-import tech.powerjob.worker.core.processor.TaskContext;
-import tech.powerjob.worker.core.processor.sdk.BasicProcessor;
-import tech.powerjob.worker.log.OmsLogger;
-
-import java.util.Optional;
-
-/**
- * @author Echo009
- * @since 2022/4/27
- */
-@Component
-public class SimpleProcessor implements BasicProcessor {
-
- @Override
- public ProcessResult process(TaskContext context) throws Exception {
-
- OmsLogger logger = context.getOmsLogger();
-
- String jobParams = Optional.ofNullable(context.getJobParams()).orElse("S");
- logger.info("Current context:{}", context.getWorkflowContext());
- logger.info("Current job params:{}", jobParams);
-
- // 娴嬭瘯涓枃闂 #581
- if (jobParams.contains("CN")) {
- return new ProcessResult(true, "浠诲姟鎴愬姛鍟︼紒锛侊紒");
- }
-
- return jobParams.contains("F") ? new ProcessResult(false) : new ProcessResult(true, "yeah!");
-
- }
-}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/StandaloneProcessorDemo.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/StandaloneProcessorDemo.java
deleted file mode 100644
index ea8eff3..0000000
--- a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/StandaloneProcessorDemo.java
+++ /dev/null
@@ -1,51 +0,0 @@
-package org.dromara.job.processors;
-
-import lombok.extern.slf4j.Slf4j;
-import org.apache.commons.lang3.StringUtils;
-import org.springframework.stereotype.Component;
-import tech.powerjob.worker.core.processor.ProcessResult;
-import tech.powerjob.worker.core.processor.TaskContext;
-import tech.powerjob.worker.core.processor.sdk.BasicProcessor;
-import tech.powerjob.worker.log.OmsLogger;
-
-import java.util.Collections;
-
-/**
- * 鍗曟満澶勭悊鍣� 绀轰緥
- *
- * @author tjq
- * @since 2020/4/17
- */
-@Slf4j
-@Component
-public class StandaloneProcessorDemo implements BasicProcessor {
-
- @Override
- public ProcessResult process(TaskContext context) throws Exception {
- OmsLogger omsLogger = context.getOmsLogger();
- omsLogger.info("StandaloneProcessorDemo start process,context is {}.", context);
- omsLogger.info("Notice! If you want this job process failed, your jobParams need to be 'failed'");
- omsLogger.info("Let's test the exception~");
- // 娴嬭瘯寮傚父鏃ュ織
- try {
- Collections.emptyList().add("277");
- } catch (Exception e) {
- omsLogger.error("oh~it seems that we have an exception~", e);
- }
- log.info("================ StandaloneProcessorDemo#process ================");
- log.info("jobParam:{}", context.getJobParams());
- log.info("instanceParams:{}", context.getInstanceParams());
- String param;
- // 瑙f瀽鍙傛暟锛岄潪澶勪簬宸ヤ綔娴佷腑鏃讹紝浼樺厛鍙栧疄渚嬪弬鏁帮紙鍏佽鍔ㄦ�乕instanceParams]瑕嗙洊闈欐�佸弬鏁癧jobParams]锛�
- if (context.getWorkflowContext() == null) {
- param = StringUtils.isBlank(context.getInstanceParams()) ? context.getJobParams() : context.getInstanceParams();
- } else {
- param = context.getJobParams();
- }
- // 鏍规嵁鍙傛暟鍒ゆ柇鏄惁鎴愬姛
- boolean success = !"failed".equals(param);
- omsLogger.info("StandaloneProcessorDemo finished process,success: {}", success);
- omsLogger.info("anyway, we finished the job successfully~Congratulations!");
- return new ProcessResult(success, context + ": " + success);
- }
-}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/TimeoutProcessor.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/TimeoutProcessor.java
deleted file mode 100644
index 4b5899f..0000000
--- a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/processors/TimeoutProcessor.java
+++ /dev/null
@@ -1,25 +0,0 @@
-package org.dromara.job.processors;
-
-import lombok.extern.slf4j.Slf4j;
-import org.springframework.stereotype.Component;
-import tech.powerjob.worker.core.processor.ProcessResult;
-import tech.powerjob.worker.core.processor.TaskContext;
-import tech.powerjob.worker.core.processor.sdk.BasicProcessor;
-
-/**
- * 娴嬭瘯瓒呮椂浠诲姟锛堝彲涓柇锛�
- *
- * @author tjq
- * @since 2020/4/20
- */
-@Component
-@Slf4j
-public class TimeoutProcessor implements BasicProcessor {
- @Override
- public ProcessResult process(TaskContext context) throws Exception {
- long sleepTime = Long.parseLong(context.getJobParams());
- log.info("TaskInstance({}) will sleep {} ms", context.getInstanceId(), sleepTime);
- Thread.sleep(Long.parseLong(context.getJobParams()));
- return new ProcessResult(true, "impossible~~~~QAQ~");
- }
-}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/snailjob/TestAnnoJobExecutor.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/snailjob/TestAnnoJobExecutor.java
new file mode 100644
index 0000000..5bea9da
--- /dev/null
+++ b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/snailjob/TestAnnoJobExecutor.java
@@ -0,0 +1,23 @@
+package org.dromara.job.snailjob;
+
+import com.aizuda.snailjob.client.job.core.annotation.JobExecutor;
+import com.aizuda.snailjob.client.job.core.dto.JobArgs;
+import com.aizuda.snailjob.client.model.ExecuteResult;
+import com.aizuda.snailjob.common.core.util.JsonUtil;
+import com.aizuda.snailjob.common.log.SnailJobLog;
+import org.springframework.stereotype.Component;
+
+/**
+ * @author opensnail
+ * @date 2024-05-17
+ */
+@Component
+@JobExecutor(name = "testJobExecutor")
+public class TestAnnoJobExecutor {
+
+ public ExecuteResult jobExecute(JobArgs jobArgs) {
+ SnailJobLog.LOCAL.info("testJobExecutor. jobArgs:{}", JsonUtil.toJsonString(jobArgs));
+ SnailJobLog.REMOTE.info("testJobExecutor. jobArgs:{}", JsonUtil.toJsonString(jobArgs));
+ return ExecuteResult.success("娴嬭瘯鎴愬姛");
+ }
+}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/snailjob/TestClassJobExecutor.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/snailjob/TestClassJobExecutor.java
new file mode 100644
index 0000000..6f7c21f
--- /dev/null
+++ b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/snailjob/TestClassJobExecutor.java
@@ -0,0 +1,19 @@
+package org.dromara.job.snailjob;
+
+import com.aizuda.snailjob.client.job.core.dto.JobArgs;
+import com.aizuda.snailjob.client.job.core.executor.AbstractJobExecutor;
+import com.aizuda.snailjob.client.model.ExecuteResult;
+import org.springframework.stereotype.Component;
+
+/**
+ * @author opensnail
+ * @date 2024-05-17
+ */
+@Component
+public class TestClassJobExecutor extends AbstractJobExecutor {
+
+ @Override
+ protected ExecuteResult doJobExecute(JobArgs jobArgs) {
+ return ExecuteResult.success("TestJobExecutor娴嬭瘯鎴愬姛");
+ }
+}
diff --git a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/workflow/WorkflowStandaloneProcessor.java b/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/workflow/WorkflowStandaloneProcessor.java
deleted file mode 100644
index 51187e3..0000000
--- a/ruoyi-modules/ruoyi-job/src/main/java/org/dromara/job/workflow/WorkflowStandaloneProcessor.java
+++ /dev/null
@@ -1,36 +0,0 @@
-package org.dromara.job.workflow;
-
-import com.alibaba.fastjson.JSON;
-import lombok.extern.slf4j.Slf4j;
-import org.springframework.stereotype.Component;
-import tech.powerjob.worker.core.processor.ProcessResult;
-import tech.powerjob.worker.core.processor.TaskContext;
-import tech.powerjob.worker.core.processor.sdk.BasicProcessor;
-import tech.powerjob.worker.log.OmsLogger;
-
-import java.util.Map;
-
-/**
- * 宸ヤ綔娴佹祴璇�
- *
- * @author tjq
- * @since 2020/6/2
- */
-@Component
-@Slf4j
-public class WorkflowStandaloneProcessor implements BasicProcessor {
-
- @Override
- public ProcessResult process(TaskContext context) throws Exception {
- OmsLogger logger = context.getOmsLogger();
- logger.info("current jobParams: {}", context.getJobParams());
- logger.info("current context: {}", context.getWorkflowContext());
- log.info("jobParams:{}", context.getJobParams());
- log.info("currentContext:{}", JSON.toJSONString(context));
-
- // 灏濊瘯鑾峰彇涓婃父浠诲姟
- Map<String, String> workflowContext = context.getWorkflowContext().fetchWorkflowContext();
- log.info("宸ヤ綔娴佷笂涓嬫枃鏁版嵁:{}", workflowContext);
- return new ProcessResult(true, context.getJobId() + " process successfully.");
- }
-}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/monitor/SysUserOnlineController.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/monitor/SysUserOnlineController.java
index def448d..9b08c2d 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/monitor/SysUserOnlineController.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/monitor/SysUserOnlineController.java
@@ -21,6 +21,7 @@
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
+import java.util.stream.Collectors;
/**
* 鍦ㄧ嚎鐢ㄦ埛鐩戞帶
@@ -87,4 +88,43 @@
}
return R.ok();
}
+
+ /**
+ * 鑾峰彇褰撳墠鐢ㄦ埛鐧诲綍鍦ㄧ嚎璁惧
+ */
+ @GetMapping()
+ public TableDataInfo<SysUserOnline> getInfo() {
+ // 鑾峰彇鎸囧畾璐﹀彿 id 鐨� token 闆嗗悎
+ List<String> tokenIds = StpUtil.getTokenValueListByLoginId(StpUtil.getLoginIdAsString());
+ List<UserOnlineDTO> userOnlineDTOList = tokenIds.stream()
+ .filter(token -> StpUtil.stpLogic.getTokenActiveTimeoutByToken(token) >= -1)
+ .map(token -> (UserOnlineDTO) RedisUtils.getCacheObject(CacheConstants.ONLINE_TOKEN_KEY + token))
+ .collect(Collectors.toList());
+ //澶嶅埗鍜屽鐞� SysUserOnline 瀵硅薄鍒楄〃
+ Collections.reverse(userOnlineDTOList);
+ userOnlineDTOList.removeAll(Collections.singleton(null));
+ List<SysUserOnline> userOnlineList = BeanUtil.copyToList(userOnlineDTOList, SysUserOnline.class);
+ return TableDataInfo.build(userOnlineList);
+ }
+
+ /**
+ * 寮洪��褰撳墠鍦ㄧ嚎璁惧
+ *
+ * @param tokenId token鍊�
+ */
+ @Log(title = "鍦ㄧ嚎璁惧", businessType = BusinessType.FORCE)
+ @PostMapping("/{tokenId}")
+ public R<Void> remove(@PathVariable("tokenId") String tokenId) {
+ try {
+ // 鑾峰彇鎸囧畾璐﹀彿 id 鐨� token 闆嗗悎
+ List<String> keys = StpUtil.getTokenValueListByLoginId(StpUtil.getLoginIdAsString());
+ keys.stream()
+ .filter(key -> key.equals(tokenId))
+ .findFirst()
+ .ifPresent(key -> StpUtil.kickoutByTokenValue(tokenId));
+ } catch (NotLoginException ignored) {
+ }
+ return R.ok();
+ }
+
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysClientController.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysClientController.java
index 61d30c7..13be4a4 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysClientController.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysClientController.java
@@ -97,7 +97,7 @@
@Log(title = "瀹㈡埛绔鐞�", businessType = BusinessType.UPDATE)
@PutMapping("/changeStatus")
public R<Void> changeStatus(@RequestBody SysClientBo bo) {
- return toAjax(sysClientService.updateUserStatus(bo.getId(), bo.getStatus()));
+ return toAjax(sysClientService.updateUserStatus(bo.getClientId(), bo.getStatus()));
}
/**
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDeptController.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDeptController.java
index 130c0d1..98b76e4 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDeptController.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDeptController.java
@@ -2,6 +2,7 @@
import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.hutool.core.convert.Convert;
+import lombok.RequiredArgsConstructor;
import org.dromara.common.core.constant.UserConstants;
import org.dromara.common.core.domain.R;
import org.dromara.common.core.utils.StringUtils;
@@ -11,7 +12,6 @@
import org.dromara.system.domain.bo.SysDeptBo;
import org.dromara.system.domain.vo.SysDeptVo;
import org.dromara.system.service.ISysDeptService;
-import lombok.RequiredArgsConstructor;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
@@ -75,6 +75,8 @@
public R<Void> add(@Validated @RequestBody SysDeptBo dept) {
if (!deptService.checkDeptNameUnique(dept)) {
return R.fail("鏂板閮ㄩ棬'" + dept.getDeptName() + "'澶辫触锛岄儴闂ㄥ悕绉板凡瀛樺湪");
+ } else if (StringUtils.isNotBlank(dept.getDeptCategory()) && !deptService.checkDeptCategoryUnique(dept)) {
+ return R.fail("鏂板閮ㄩ棬'" + dept.getDeptName() + "'澶辫触锛岄儴闂ㄧ被鍒紪鐮佸凡瀛樺湪");
}
return toAjax(deptService.insertDept(dept));
}
@@ -90,6 +92,8 @@
deptService.checkDeptDataScope(deptId);
if (!deptService.checkDeptNameUnique(dept)) {
return R.fail("淇敼閮ㄩ棬'" + dept.getDeptName() + "'澶辫触锛岄儴闂ㄥ悕绉板凡瀛樺湪");
+ } else if (StringUtils.isNotBlank(dept.getDeptCategory()) && !deptService.checkDeptCategoryUnique(dept)) {
+ return R.fail("淇敼閮ㄩ棬'" + dept.getDeptName() + "'澶辫触锛岄儴闂ㄧ被鍒紪鐮佸凡瀛樺湪");
} else if (dept.getParentId().equals(deptId)) {
return R.fail("淇敼閮ㄩ棬'" + dept.getDeptName() + "'澶辫触锛屼笂绾ч儴闂ㄤ笉鑳芥槸鑷繁");
} else if (StringUtils.equals(UserConstants.DEPT_DISABLE, dept.getStatus())) {
@@ -120,4 +124,16 @@
deptService.checkDeptDataScope(deptId);
return toAjax(deptService.deleteDeptById(deptId));
}
+
+ /**
+ * 鑾峰彇閮ㄩ棬閫夋嫨妗嗗垪琛�
+ *
+ * @param deptIds 閮ㄩ棬ID涓�
+ */
+ @SaCheckPermission("system:dept:query")
+ @GetMapping("/optionselect")
+ public R<List<SysDeptVo>> optionselect(@RequestParam(required = false) Long[] deptIds) {
+ return R.ok(deptService.selectDeptByIds(deptIds == null ? null : List.of(deptIds)));
+ }
+
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDictDataController.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDictDataController.java
index cc8034e..5752751 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDictDataController.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysDictDataController.java
@@ -87,6 +87,9 @@
@Log(title = "瀛楀吀鏁版嵁", businessType = BusinessType.INSERT)
@PostMapping
public R<Void> add(@Validated @RequestBody SysDictDataBo dict) {
+ if (!dictDataService.checkDictDataUnique(dict)) {
+ return R.fail("鏂板瀛楀吀鏁版嵁'" + dict.getDictValue() + "'澶辫触锛屽瓧鍏搁敭鍊煎凡瀛樺湪");
+ }
dictDataService.insertDictData(dict);
return R.ok();
}
@@ -98,6 +101,9 @@
@Log(title = "瀛楀吀鏁版嵁", businessType = BusinessType.UPDATE)
@PutMapping
public R<Void> edit(@Validated @RequestBody SysDictDataBo dict) {
+ if (!dictDataService.checkDictDataUnique(dict)) {
+ return R.fail("淇敼瀛楀吀鏁版嵁'" + dict.getDictValue() + "'澶辫触锛屽瓧鍏搁敭鍊煎凡瀛樺湪");
+ }
dictDataService.updateDictData(dict);
return R.ok();
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysPostController.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysPostController.java
index fe62fdb..782bcfc 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysPostController.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysPostController.java
@@ -1,6 +1,9 @@
package org.dromara.system.controller.system;
import cn.dev33.satoken.annotation.SaCheckPermission;
+import cn.hutool.core.util.ObjectUtil;
+import jakarta.servlet.http.HttpServletResponse;
+import lombok.RequiredArgsConstructor;
import org.dromara.common.core.constant.UserConstants;
import org.dromara.common.core.domain.R;
import org.dromara.common.excel.utils.ExcelUtil;
@@ -12,11 +15,10 @@
import org.dromara.system.domain.bo.SysPostBo;
import org.dromara.system.domain.vo.SysPostVo;
import org.dromara.system.service.ISysPostService;
-import jakarta.servlet.http.HttpServletResponse;
-import lombok.RequiredArgsConstructor;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
+import java.util.ArrayList;
import java.util.List;
/**
@@ -110,12 +112,22 @@
/**
* 鑾峰彇宀椾綅閫夋嫨妗嗗垪琛�
+ *
+ * @param postIds 宀椾綅ID涓�
+ * @param deptId 閮ㄩ棬id
*/
+ @SaCheckPermission("system:post:query")
@GetMapping("/optionselect")
- public R<List<SysPostVo>> optionselect() {
- SysPostBo postBo = new SysPostBo();
- postBo.setStatus(UserConstants.POST_NORMAL);
- List<SysPostVo> posts = postService.selectPostList(postBo);
- return R.ok(posts);
+ public R<List<SysPostVo>> optionselect(@RequestParam(required = false) Long[] postIds, @RequestParam(required = false) Long deptId) {
+ List<SysPostVo> list = new ArrayList<>();
+ if (ObjectUtil.isNotNull(deptId)) {
+ SysPostBo post = new SysPostBo();
+ post.setDeptId(deptId);
+ list = postService.selectPostList(post);
+ } else if (postIds != null) {
+ list = postService.selectPostByIds(List.of(postIds));
+ }
+ return R.ok(list);
}
+
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysProfileController.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysProfileController.java
index f9c4b3d..0cdb675 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysProfileController.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysProfileController.java
@@ -19,6 +19,7 @@
import org.dromara.system.domain.vo.SysOssVo;
import org.dromara.system.domain.vo.SysUserVo;
import org.dromara.system.service.ISysOssService;
+import org.dromara.system.service.ISysRoleService;
import org.dromara.system.service.ISysUserService;
import lombok.RequiredArgsConstructor;
import org.springframework.http.MediaType;
@@ -50,8 +51,8 @@
SysUserVo user = userService.selectUserById(LoginHelper.getUserId());
ProfileVo profileVo = new ProfileVo();
profileVo.setUser(user);
- profileVo.setRoleGroup(userService.selectUserRoleGroup(user.getUserName()));
- profileVo.setPostGroup(userService.selectUserPostGroup(user.getUserName()));
+ profileVo.setRoleGroup(userService.selectUserRoleGroup(user.getUserId()));
+ profileVo.setPostGroup(userService.selectUserPostGroup(user.getUserId()));
return R.ok(profileVo);
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysRoleController.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysRoleController.java
index 3a9418b..d4a9dc8 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysRoleController.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysRoleController.java
@@ -149,11 +149,13 @@
/**
* 鑾峰彇瑙掕壊閫夋嫨妗嗗垪琛�
+ *
+ * @param roleIds 瑙掕壊ID涓�
*/
@SaCheckPermission("system:role:query")
@GetMapping("/optionselect")
- public R<List<SysRoleVo>> optionselect() {
- return R.ok(roleService.selectRoleAll());
+ public R<List<SysRoleVo>> optionselect(@RequestParam(required = false) Long[] roleIds) {
+ return R.ok(roleService.selectRoleByIds(roleIds == null ? null : List.of(roleIds)));
}
/**
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysUserController.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysUserController.java
index beefe4a..36104d6 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysUserController.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/controller/system/SysUserController.java
@@ -11,7 +11,6 @@
import org.dromara.common.core.constant.UserConstants;
import org.dromara.common.core.domain.R;
import org.dromara.common.core.domain.model.LoginUser;
-import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.common.core.utils.StreamUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.encrypt.annotation.ApiEncrypt;
@@ -72,9 +71,8 @@
@SaCheckPermission("system:user:export")
@PostMapping("/export")
public void export(SysUserBo user, HttpServletResponse response) {
- List<SysUserVo> list = userService.selectUserList(user);
- List<SysUserExportVo> listVo = MapstructUtils.convert(list, SysUserExportVo.class);
- ExcelUtil.exportExcel(listVo, "鐢ㄦ埛鏁版嵁", SysUserExportVo.class, response);
+ List<SysUserExportVo> list = userService.selectUserExportList(user);
+ ExcelUtil.exportExcel(list, "鐢ㄦ埛鏁版嵁", SysUserExportVo.class, response);
}
/**
@@ -134,16 +132,19 @@
SysUserInfoVo userInfoVo = new SysUserInfoVo();
SysRoleBo roleBo = new SysRoleBo();
roleBo.setStatus(UserConstants.ROLE_NORMAL);
- SysPostBo postBo = new SysPostBo();
- postBo.setStatus(UserConstants.POST_NORMAL);
List<SysRoleVo> roles = roleService.selectRoleList(roleBo);
userInfoVo.setRoles(LoginHelper.isSuperAdmin(userId) ? roles : StreamUtils.filter(roles, r -> !r.isSuperAdmin()));
- userInfoVo.setPosts(postService.selectPostList(postBo));
if (ObjectUtil.isNotNull(userId)) {
SysUserVo sysUser = userService.selectUserById(userId);
userInfoVo.setUser(sysUser);
- userInfoVo.setRoleIds(StreamUtils.toList(sysUser.getRoles(), SysRoleVo::getRoleId));
- userInfoVo.setPostIds(postService.selectPostListByUserId(userId));
+ userInfoVo.setRoleIds(roleService.selectRoleListByUserId(userId));
+ Long deptId = sysUser.getDeptId();
+ if (ObjectUtil.isNotNull(deptId)) {
+ SysPostBo postBo = new SysPostBo();
+ postBo.setDeptId(deptId);
+ userInfoVo.setPosts(postService.selectPostList(postBo));
+ userInfoVo.setPostIds(postService.selectPostListByUserId(userId));
+ }
}
return R.ok(userInfoVo);
}
@@ -208,6 +209,19 @@
}
/**
+ * 鏍规嵁鐢ㄦ埛ID涓叉壒閲忚幏鍙栫敤鎴峰熀纭�淇℃伅
+ *
+ * @param userIds 鐢ㄦ埛ID涓�
+ * @param deptId 閮ㄩ棬ID
+ */
+ @SaCheckPermission("system:user:query")
+ @GetMapping("/optionselect")
+ public R<List<SysUserVo>> optionselect(@RequestParam(required = false) Long[] userIds,
+ @RequestParam(required = false) Long deptId) {
+ return R.ok(userService.selectUserByIds(userIds == null ? null : List.of(userIds), deptId));
+ }
+
+ /**
* 閲嶇疆瀵嗙爜
*/
@ApiEncrypt
@@ -241,8 +255,9 @@
@SaCheckPermission("system:user:query")
@GetMapping("/authRole/{userId}")
public R<SysUserInfoVo> authRole(@PathVariable Long userId) {
+ userService.checkUserDataScope(userId);
SysUserVo user = userService.selectUserById(userId);
- List<SysRoleVo> roles = roleService.selectRolesByUserId(userId);
+ List<SysRoleVo> roles = roleService.selectRolesAuthByUserId(userId);
SysUserInfoVo userInfoVo = new SysUserInfoVo();
userInfoVo.setUser(user);
userInfoVo.setRoles(LoginHelper.isSuperAdmin(userId) ? roles : StreamUtils.filter(roles, r -> !r.isSuperAdmin()));
@@ -281,4 +296,5 @@
public R<List<SysUserVo>> listByDept(@PathVariable @NotNull Long deptId) {
return R.ok(userService.selectUserListByDept(deptId));
}
+
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysDept.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysDept.java
index 70f1a9a..48ca682 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysDept.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysDept.java
@@ -3,9 +3,9 @@
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableLogic;
import com.baomidou.mybatisplus.annotation.TableName;
-import org.dromara.common.tenant.core.TenantEntity;
import lombok.Data;
import lombok.EqualsAndHashCode;
+import org.dromara.common.tenant.core.TenantEntity;
import java.io.Serial;
@@ -40,6 +40,11 @@
private String deptName;
/**
+ * 閮ㄩ棬绫诲埆缂栫爜
+ */
+ private String deptCategory;
+
+ /**
* 鏄剧ず椤哄簭
*/
private Integer orderNum;
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysOssConfig.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysOssConfig.java
index 8a9e25e..4b67d63 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysOssConfig.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysOssConfig.java
@@ -17,7 +17,7 @@
public class SysOssConfig extends BaseEntity {
/**
- * 涓诲缓
+ * 涓婚敭
*/
@TableId(value = "oss_config_id")
private Long ossConfigId;
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysPost.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysPost.java
index 7fe7039..2c985da 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysPost.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysPost.java
@@ -24,6 +24,11 @@
private Long postId;
/**
+ * 閮ㄩ棬id
+ */
+ private Long deptId;
+
+ /**
* 宀椾綅缂栫爜
*/
private String postCode;
@@ -34,6 +39,11 @@
private String postName;
/**
+ * 宀椾綅绫诲埆缂栫爜
+ */
+ private String postCategory;
+
+ /**
* 宀椾綅鎺掑簭
*/
private Integer postSort;
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysUserOnline.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysUserOnline.java
index 6def906..ba30eb6 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysUserOnline.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/SysUserOnline.java
@@ -7,7 +7,6 @@
*
* @author Lion Li
*/
-
@Data
public class SysUserOnline {
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDeptBo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDeptBo.java
index a5031d7..5f64d6f 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDeptBo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDeptBo.java
@@ -39,6 +39,12 @@
private String deptName;
/**
+ * 閮ㄩ棬绫诲埆缂栫爜
+ */
+ @Size(min = 0, max = 100, message = "閮ㄩ棬绫诲埆缂栫爜闀垮害涓嶈兘瓒呰繃{max}涓瓧绗�")
+ private String deptCategory;
+
+ /**
* 鏄剧ず椤哄簭
*/
@NotNull(message = "鏄剧ず椤哄簭涓嶈兘涓虹┖")
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDictTypeBo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDictTypeBo.java
index 39257f7..fcc1ac1 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDictTypeBo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysDictTypeBo.java
@@ -6,6 +6,7 @@
import jakarta.validation.constraints.Size;
import lombok.Data;
import lombok.EqualsAndHashCode;
+import org.dromara.common.core.constant.RegexConstants;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import org.dromara.system.domain.SysDictType;
@@ -37,7 +38,7 @@
*/
@NotBlank(message = "瀛楀吀绫诲瀷涓嶈兘涓虹┖")
@Size(min = 0, max = 100, message = "瀛楀吀绫诲瀷绫诲瀷闀垮害涓嶈兘瓒呰繃{max}涓瓧绗�")
- @Pattern(regexp = "^[a-z][a-z0-9_]*$", message = "瀛楀吀绫诲瀷蹇呴』浠ュ瓧姣嶅紑澶达紝涓斿彧鑳戒负锛堝皬鍐欏瓧姣嶏紝鏁板瓧锛屼笅婊戠嚎锛�")
+ @Pattern(regexp = RegexConstants.DICTIONARY_TYPE, message = "瀛楀吀绫诲瀷蹇呴』浠ュ瓧姣嶅紑澶达紝涓斿彧鑳戒负锛堝皬鍐欏瓧姣嶏紝鏁板瓧锛屼笅婊戠嚎锛�")
private String dictType;
/**
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysMenuBo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysMenuBo.java
index 498280a..fbaafaa 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysMenuBo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysMenuBo.java
@@ -4,9 +4,11 @@
import io.github.linpeilie.annotations.AutoMapper;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
+import jakarta.validation.constraints.Pattern;
import jakarta.validation.constraints.Size;
import lombok.Data;
import lombok.EqualsAndHashCode;
+import org.dromara.common.core.constant.RegexConstants;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import org.dromara.system.domain.SysMenu;
@@ -92,6 +94,7 @@
*/
@JsonInclude(JsonInclude.Include.NON_NULL)
@Size(min = 0, max = 100, message = "鏉冮檺鏍囪瘑闀垮害涓嶈兘瓒呰繃{max}涓瓧绗�")
+ @Pattern(regexp = RegexConstants.PERMISSION_STRING, message = "鏉冮檺鏍囪瘑蹇呴』绗﹀悎 tool:build:list 鏍煎紡")
private String perms;
/**
@@ -103,6 +106,5 @@
* 澶囨敞
*/
private String remark;
-
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysOssConfigBo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysOssConfigBo.java
index 5887ded..3dc4328 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysOssConfigBo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysOssConfigBo.java
@@ -25,9 +25,9 @@
public class SysOssConfigBo extends BaseEntity {
/**
- * 涓诲缓
+ * 涓婚敭
*/
- @NotNull(message = "涓诲缓涓嶈兘涓虹┖", groups = {EditGroup.class})
+ @NotNull(message = "涓婚敭涓嶈兘涓虹┖", groups = {EditGroup.class})
private Long ossConfigId;
/**
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysPostBo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysPostBo.java
index b93c39c..09805cd 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysPostBo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysPostBo.java
@@ -26,6 +26,17 @@
private Long postId;
/**
+ * 閮ㄩ棬id锛堝崟閮ㄩ棬锛�
+ */
+ @NotNull(message = "閮ㄩ棬id涓嶈兘涓虹┖")
+ private Long deptId;
+
+ /**
+ * 褰掑睘閮ㄩ棬id锛堥儴闂ㄦ爲锛�
+ */
+ private Long belongDeptId;
+
+ /**
* 宀椾綅缂栫爜
*/
@NotBlank(message = "宀椾綅缂栫爜涓嶈兘涓虹┖")
@@ -38,6 +49,12 @@
@NotBlank(message = "宀椾綅鍚嶇О涓嶈兘涓虹┖")
@Size(min = 0, max = 50, message = "宀椾綅鍚嶇О闀垮害涓嶈兘瓒呰繃{max}涓瓧绗�")
private String postName;
+
+ /**
+ * 宀椾綅绫诲埆缂栫爜
+ */
+ @Size(min = 0, max = 100, message = "绫诲埆缂栫爜闀垮害涓嶈兘瓒呰繃{max}涓瓧绗�")
+ private String postCategory;
/**
* 鏄剧ず椤哄簭
@@ -54,6 +71,5 @@
* 澶囨敞
*/
private String remark;
-
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysSocialBo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysSocialBo.java
index 7784271..cede1e9 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysSocialBo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysSocialBo.java
@@ -29,9 +29,9 @@
private Long id;
/**
- * 鐨勫敮涓�ID
+ * 璁よ瘉鍞竴ID
*/
- @NotBlank(message = "鐨勫敮涓�ID涓嶈兘涓虹┖", groups = { AddGroup.class, EditGroup.class })
+ @NotBlank(message = "璁よ瘉鍞竴ID涓嶈兘涓虹┖", groups = { AddGroup.class, EditGroup.class })
private String authId;
/**
@@ -64,7 +64,7 @@
/**
* 鐢ㄦ埛鐨� ID
*/
- @NotBlank(message = "鐢ㄦ埛鐨� ID涓嶈兘涓虹┖", groups = { AddGroup.class, EditGroup.class })
+ @NotBlank(message = "鐢ㄦ埛鐨処D涓嶈兘涓虹┖", groups = { AddGroup.class, EditGroup.class })
private Long userId;
/**
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysUserBo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysUserBo.java
index 011254e..7ad2759 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysUserBo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/bo/SysUserBo.java
@@ -103,6 +103,11 @@
*/
private Long roleId;
+ /**
+ * 鎺掗櫎涓嶆煡璇㈢殑鐢ㄦ埛(宸ヤ綔娴佺敤)
+ */
+ private String excludeUserIds;
+
public SysUserBo(Long userId) {
this.userId = userId;
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysDeptVo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysDeptVo.java
index c4dd412..c56fb09 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysDeptVo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysDeptVo.java
@@ -53,6 +53,12 @@
private String deptName;
/**
+ * 閮ㄩ棬绫诲埆缂栫爜
+ */
+ @ExcelProperty(value = "閮ㄩ棬绫诲埆缂栫爜")
+ private String deptCategory;
+
+ /**
* 鏄剧ず椤哄簭
*/
private Integer orderNum;
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysOssConfigVo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysOssConfigVo.java
index b88ec40..e7cfde4 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysOssConfigVo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysOssConfigVo.java
@@ -25,7 +25,7 @@
private static final long serialVersionUID = 1L;
/**
- * 涓诲缓
+ * 涓婚敭
*/
private Long ossConfigId;
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysPostVo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysPostVo.java
index 3e6c6a8..69be547 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysPostVo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysPostVo.java
@@ -2,17 +2,17 @@
import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
import com.alibaba.excel.annotation.ExcelProperty;
-import org.dromara.common.excel.annotation.ExcelDictFormat;
-import org.dromara.common.excel.convert.ExcelDictConvert;
-import org.dromara.system.domain.SysPost;
import io.github.linpeilie.annotations.AutoMapper;
import lombok.Data;
+import org.dromara.common.excel.annotation.ExcelDictFormat;
+import org.dromara.common.excel.convert.ExcelDictConvert;
+import org.dromara.common.translation.annotation.Translation;
+import org.dromara.common.translation.constant.TransConstant;
+import org.dromara.system.domain.SysPost;
import java.io.Serial;
import java.io.Serializable;
import java.util.Date;
-
-
/**
* 宀椾綅淇℃伅瑙嗗浘瀵硅薄 sys_post
@@ -34,6 +34,12 @@
private Long postId;
/**
+ * 閮ㄩ棬id
+ */
+ @ExcelProperty(value = "閮ㄩ棬id")
+ private Long deptId;
+
+ /**
* 宀椾綅缂栫爜
*/
@ExcelProperty(value = "宀椾綅缂栫爜")
@@ -44,6 +50,12 @@
*/
@ExcelProperty(value = "宀椾綅鍚嶇О")
private String postName;
+
+ /**
+ * 宀椾綅绫诲埆缂栫爜
+ */
+ @ExcelProperty(value = "绫诲埆缂栫爜")
+ private String postCategory;
/**
* 鏄剧ず椤哄簭
@@ -70,4 +82,10 @@
@ExcelProperty(value = "鍒涘缓鏃堕棿")
private Date createTime;
+ /**
+ * 閮ㄩ棬鍚�
+ */
+ @Translation(type = TransConstant.DEPT_ID_TO_NAME, mapper = "deptId")
+ private String deptName;
+
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserExportVo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserExportVo.java
index 3cc5186..37ec6b7 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserExportVo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserExportVo.java
@@ -20,7 +20,6 @@
@Data
@NoArgsConstructor
-@AutoMapper(target = SysUserVo.class, convertGenerate = false)
public class SysUserExportVo implements Serializable {
@Serial
@@ -85,14 +84,12 @@
/**
* 閮ㄩ棬鍚嶇О
*/
- @ReverseAutoMapping(target = "deptName", source = "dept.deptName")
@ExcelProperty(value = "閮ㄩ棬鍚嶇О")
private String deptName;
/**
* 璐熻矗浜�
*/
- @ReverseAutoMapping(target = "leaderName", source = "dept.leaderName")
@ExcelProperty(value = "閮ㄩ棬璐熻矗浜�")
private String leaderName;
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserVo.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserVo.java
index 7db91d1..d1f4059 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserVo.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/domain/vo/SysUserVo.java
@@ -114,9 +114,10 @@
private Date createTime;
/**
- * 閮ㄩ棬瀵硅薄
+ * 閮ㄩ棬鍚�
*/
- private SysDeptVo dept;
+ @Translation(type = TransConstant.DEPT_ID_TO_NAME, mapper = "deptId")
+ private String deptName;
/**
* 瑙掕壊瀵硅薄
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysDeptMapper.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysDeptMapper.java
index 45ad77e..08dda66 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysDeptMapper.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysDeptMapper.java
@@ -32,7 +32,7 @@
@DataPermission({
@DataColumn(key = "deptName", value = "dept_id")
})
- SysDeptVo selectDeptById(Long deptId);
+ long countDeptById(Long deptId);
/**
* 鏍规嵁瑙掕壊ID鏌ヨ閮ㄩ棬鏍戜俊鎭�
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysPostMapper.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysPostMapper.java
index 48e6a12..f9bf134 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysPostMapper.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysPostMapper.java
@@ -1,5 +1,11 @@
package org.dromara.system.mapper;
+import com.baomidou.mybatisplus.core.conditions.Wrapper;
+import com.baomidou.mybatisplus.core.toolkit.Constants;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import org.apache.ibatis.annotations.Param;
+import org.dromara.common.mybatis.annotation.DataColumn;
+import org.dromara.common.mybatis.annotation.DataPermission;
import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
import org.dromara.system.domain.SysPost;
import org.dromara.system.domain.vo.SysPostVo;
@@ -13,20 +19,18 @@
*/
public interface SysPostMapper extends BaseMapperPlus<SysPost, SysPostVo> {
- /**
- * 鏍规嵁鐢ㄦ埛ID鑾峰彇宀椾綅閫夋嫨妗嗗垪琛�
- *
- * @param userId 鐢ㄦ埛ID
- * @return 閫変腑宀椾綅ID鍒楄〃
- */
- List<Long> selectPostListByUserId(Long userId);
+ @DataPermission({
+ @DataColumn(key = "deptName", value = "dept_id"),
+ @DataColumn(key = "userName", value = "create_by")
+ })
+ Page<SysPostVo> selectPagePostList(@Param("page") Page<SysPostVo> page, @Param(Constants.WRAPPER) Wrapper<SysPost> queryWrapper);
/**
* 鏌ヨ鐢ㄦ埛鎵�灞炲矖浣嶇粍
*
- * @param userName 鐢ㄦ埛鍚�
+ * @param userId 鐢ㄦ埛ID
* @return 缁撴灉
*/
- List<SysPostVo> selectPostsByUserName(String userName);
+ List<SysPostVo> selectPostsByUserId(Long userId);
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysRoleMapper.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysRoleMapper.java
index 55ca769..ac5a47e 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysRoleMapper.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysRoleMapper.java
@@ -3,12 +3,12 @@
import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.toolkit.Constants;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import org.apache.ibatis.annotations.Param;
import org.dromara.common.mybatis.annotation.DataColumn;
import org.dromara.common.mybatis.annotation.DataPermission;
import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
import org.dromara.system.domain.SysRole;
import org.dromara.system.domain.vo.SysRoleVo;
-import org.apache.ibatis.annotations.Param;
import java.util.List;
@@ -51,21 +51,12 @@
*/
List<SysRoleVo> selectRolePermissionByUserId(Long userId);
-
- /**
- * 鏍规嵁鐢ㄦ埛ID鑾峰彇瑙掕壊閫夋嫨妗嗗垪琛�
- *
- * @param userId 鐢ㄦ埛ID
- * @return 閫変腑瑙掕壊ID鍒楄〃
- */
- List<Long> selectRoleListByUserId(Long userId);
-
/**
* 鏍规嵁鐢ㄦ埛ID鏌ヨ瑙掕壊
*
- * @param userName 鐢ㄦ埛鍚�
+ * @param userId 鐢ㄦ埛ID
* @return 瑙掕壊鍒楄〃
*/
- List<SysRoleVo> selectRolesByUserName(String userName);
+ List<SysRoleVo> selectRolesByUserId(Long userId);
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysUserMapper.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysUserMapper.java
index 4322225..fc7fc6e 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysUserMapper.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/mapper/SysUserMapper.java
@@ -8,6 +8,7 @@
import org.dromara.common.mybatis.annotation.DataPermission;
import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
import org.dromara.system.domain.SysUser;
+import org.dromara.system.domain.vo.SysUserExportVo;
import org.dromara.system.domain.vo.SysUserVo;
import java.util.List;
@@ -20,10 +21,16 @@
public interface SysUserMapper extends BaseMapperPlus<SysUser, SysUserVo> {
@DataPermission({
- @DataColumn(key = "deptName", value = "d.dept_id"),
+ @DataColumn(key = "deptName", value = "u.dept_id"),
@DataColumn(key = "userName", value = "u.user_id")
})
Page<SysUserVo> selectPageUserList(@Param("page") Page<SysUser> page, @Param(Constants.WRAPPER) Wrapper<SysUser> queryWrapper);
+
+ @DataPermission({
+ @DataColumn(key = "deptName", value = "dept_id"),
+ @DataColumn(key = "userName", value = "user_id")
+ })
+ List<SysUserVo> selectUserList(@Param(Constants.WRAPPER) Wrapper<SysUser> queryWrapper);
/**
* 鏍规嵁鏉′欢鍒嗛〉鏌ヨ鐢ㄦ埛鍒楄〃
@@ -35,7 +42,7 @@
@DataColumn(key = "deptName", value = "d.dept_id"),
@DataColumn(key = "userName", value = "u.user_id")
})
- List<SysUserVo> selectUserList(@Param(Constants.WRAPPER) Wrapper<SysUser> queryWrapper);
+ List<SysUserExportVo> selectUserExportList(@Param(Constants.WRAPPER) Wrapper<SysUser> queryWrapper);
/**
* 鏍规嵁鏉′欢鍒嗛〉鏌ヨ宸查厤鐢ㄦ埛瑙掕壊鍒楄〃
@@ -61,41 +68,11 @@
})
Page<SysUserVo> selectUnallocatedList(@Param("page") Page<SysUser> page, @Param(Constants.WRAPPER) Wrapper<SysUser> queryWrapper);
- /**
- * 閫氳繃鐢ㄦ埛鍚嶆煡璇㈢敤鎴�
- *
- * @param userName 鐢ㄦ埛鍚�
- * @return 鐢ㄦ埛瀵硅薄淇℃伅
- */
- SysUserVo selectUserByUserName(String userName);
-
- /**
- * 閫氳繃鎵嬫満鍙锋煡璇㈢敤鎴�
- *
- * @param phonenumber 鎵嬫満鍙�
- * @return 鐢ㄦ埛瀵硅薄淇℃伅
- */
- SysUserVo selectUserByPhonenumber(String phonenumber);
-
- /**
- * 閫氳繃閭鏌ヨ鐢ㄦ埛
- *
- * @param email 閭
- * @return 鐢ㄦ埛瀵硅薄淇℃伅
- */
- SysUserVo selectUserByEmail(String email);
-
- /**
- * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛
- *
- * @param userId 鐢ㄦ埛ID
- * @return 鐢ㄦ埛瀵硅薄淇℃伅
- */
@DataPermission({
- @DataColumn(key = "deptName", value = "d.dept_id"),
- @DataColumn(key = "userName", value = "u.user_id")
+ @DataColumn(key = "deptName", value = "dept_id"),
+ @DataColumn(key = "userName", value = "user_id")
})
- SysUserVo selectUserById(Long userId);
+ long countUserById(Long userId);
@Override
@DataPermission({
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysClientService.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysClientService.java
index db48d4b..d0f8a3c 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysClientService.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysClientService.java
@@ -25,7 +25,7 @@
/**
* 鏌ヨ瀹㈡埛绔俊鎭熀浜庡鎴风id
*/
- SysClient queryByClientId(String clientId);
+ SysClientVo queryByClientId(String clientId);
/**
* 鏌ヨ瀹㈡埛绔鐞嗗垪琛�
@@ -50,7 +50,7 @@
/**
* 淇敼鐘舵��
*/
- int updateUserStatus(Long id, String status);
+ int updateUserStatus(String clientId, String status);
/**
* 鏍¢獙骞舵壒閲忓垹闄ゅ鎴风绠$悊淇℃伅
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDeptService.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDeptService.java
index b209381..cd984d8 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDeptService.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDeptService.java
@@ -53,6 +53,14 @@
SysDeptVo selectDeptById(Long deptId);
/**
+ * 閫氳繃閮ㄩ棬ID涓叉煡璇㈤儴闂�
+ *
+ * @param deptIds 閮ㄩ棬id涓�
+ * @return 閮ㄩ棬鍒楄〃淇℃伅
+ */
+ List<SysDeptVo> selectDeptByIds(List<Long> deptIds);
+
+ /**
* 鏍规嵁ID鏌ヨ鎵�鏈夊瓙閮ㄩ棬鏁帮紙姝e父鐘舵�侊級
*
* @param deptId 閮ㄩ棬ID
@@ -85,6 +93,14 @@
boolean checkDeptNameUnique(SysDeptBo dept);
/**
+ * 鏍¢獙閮ㄩ棬绫诲埆缂栫爜鏄惁鍞竴
+ *
+ * @param dept 閮ㄩ棬淇℃伅
+ * @return 缁撴灉
+ */
+ boolean checkDeptCategoryUnique(SysDeptBo dept);
+
+ /**
* 鏍¢獙閮ㄩ棬鏄惁鏈夋暟鎹潈闄�
*
* @param deptId 閮ㄩ棬id
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDictDataService.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDictDataService.java
index 30442ce..0e697db 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDictDataService.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysDictDataService.java
@@ -64,4 +64,13 @@
* @return 缁撴灉
*/
List<SysDictDataVo> updateDictData(SysDictDataBo bo);
+
+ /**
+ * 鏍¢獙瀛楀吀閿�兼槸鍚﹀敮涓�
+ *
+ * @param dict 瀛楀吀鏁版嵁
+ * @return 缁撴灉
+ */
+ boolean checkDictDataUnique(SysDictDataBo dict);
+
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssConfigService.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssConfigService.java
index a8bc57b..2f6dfc9 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssConfigService.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssConfigService.java
@@ -31,12 +31,11 @@
*/
TableDataInfo<SysOssConfigVo> queryPageList(SysOssConfigBo bo, PageQuery pageQuery);
-
/**
* 鏍规嵁鏂板涓氬姟瀵硅薄鎻掑叆瀵硅薄瀛樺偍閰嶇疆
*
* @param bo 瀵硅薄瀛樺偍閰嶇疆鏂板涓氬姟瀵硅薄
- * @return
+ * @return 缁撴灉
*/
Boolean insertByBo(SysOssConfigBo bo);
@@ -44,7 +43,7 @@
* 鏍规嵁缂栬緫涓氬姟瀵硅薄淇敼瀵硅薄瀛樺偍閰嶇疆
*
* @param bo 瀵硅薄瀛樺偍閰嶇疆缂栬緫涓氬姟瀵硅薄
- * @return
+ * @return 缁撴灉
*/
Boolean updateByBo(SysOssConfigBo bo);
@@ -53,7 +52,7 @@
*
* @param ids 涓婚敭闆嗗悎
* @param isValid 鏄惁鏍¢獙,true-鍒犻櫎鍓嶆牎楠�,false-涓嶆牎楠�
- * @return
+ * @return 缁撴灉
*/
Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid);
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssService.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssService.java
index 2dfe01f..057c068 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssService.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysOssService.java
@@ -19,18 +19,62 @@
*/
public interface ISysOssService {
+ /**
+ * 鏌ヨOSS瀵硅薄瀛樺偍鍒楄〃
+ *
+ * @param sysOss OSS瀵硅薄瀛樺偍鍒嗛〉鏌ヨ瀵硅薄
+ * @param pageQuery 鍒嗛〉鏌ヨ瀹炰綋绫�
+ * @return 缁撴灉
+ */
TableDataInfo<SysOssVo> queryPageList(SysOssBo sysOss, PageQuery pageQuery);
+ /**
+ * 鏍规嵁涓�缁� ossIds 鑾峰彇瀵瑰簲鐨� SysOssVo 鍒楄〃
+ *
+ * @param ossIds 涓�缁勬枃浠跺湪鏁版嵁搴撲腑鐨勫敮涓�鏍囪瘑闆嗗悎
+ * @return 鍖呭惈 SysOssVo 瀵硅薄鐨勫垪琛�
+ */
List<SysOssVo> listByIds(Collection<Long> ossIds);
+ /**
+ * 鏍规嵁 ossId 浠庣紦瀛樻垨鏁版嵁搴撲腑鑾峰彇 SysOssVo 瀵硅薄
+ *
+ * @param ossId 鏂囦欢鍦ㄦ暟鎹簱涓殑鍞竴鏍囪瘑
+ * @return SysOssVo 瀵硅薄锛屽寘鍚枃浠朵俊鎭�
+ */
SysOssVo getById(Long ossId);
+ /**
+ * 涓婁紶 MultipartFile 鍒板璞″瓨鍌ㄦ湇鍔★紝骞朵繚瀛樻枃浠朵俊鎭埌鏁版嵁搴�
+ *
+ * @param file 瑕佷笂浼犵殑 MultipartFile 瀵硅薄
+ * @return 涓婁紶鎴愬姛鍚庣殑 SysOssVo 瀵硅薄锛屽寘鍚枃浠朵俊鎭�
+ */
SysOssVo upload(MultipartFile file);
+ /**
+ * 涓婁紶鏂囦欢鍒板璞″瓨鍌ㄦ湇鍔★紝骞朵繚瀛樻枃浠朵俊鎭埌鏁版嵁搴�
+ *
+ * @param file 瑕佷笂浼犵殑鏂囦欢瀵硅薄
+ * @return 涓婁紶鎴愬姛鍚庣殑 SysOssVo 瀵硅薄锛屽寘鍚枃浠朵俊鎭�
+ */
SysOssVo upload(File file);
+ /**
+ * 鏂囦欢涓嬭浇鏂规硶锛屾敮鎸佷竴娆℃�т笅杞藉畬鏁存枃浠�
+ *
+ * @param ossId OSS瀵硅薄ID
+ * @param response HttpServletResponse瀵硅薄锛岀敤浜庤缃搷搴斿ご鍜屽悜瀹㈡埛绔彂閫佹枃浠跺唴瀹�
+ */
void download(Long ossId, HttpServletResponse response) throws IOException;
+ /**
+ * 鍒犻櫎OSS瀵硅薄瀛樺偍
+ *
+ * @param ids OSS瀵硅薄ID涓�
+ * @param isValid 鍒ゆ柇鏄惁闇�瑕佹牎楠�
+ * @return 缁撴灉
+ */
Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid);
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysPostService.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysPostService.java
index c6409c8..c43f039 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysPostService.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysPostService.java
@@ -49,6 +49,14 @@
List<Long> selectPostListByUserId(Long userId);
/**
+ * 閫氳繃宀椾綅ID涓叉煡璇㈠矖浣�
+ *
+ * @param postIds 宀椾綅id涓�
+ * @return 宀椾綅鍒楄〃淇℃伅
+ */
+ List<SysPostVo> selectPostByIds(List<Long> postIds);
+
+ /**
* 鏍¢獙宀椾綅鍚嶇О
*
* @param post 宀椾綅淇℃伅
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysRoleService.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysRoleService.java
index d2ee61f..64740ae 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysRoleService.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysRoleService.java
@@ -36,6 +36,14 @@
List<SysRoleVo> selectRolesByUserId(Long userId);
/**
+ * 鏍规嵁鐢ㄦ埛ID鏌ヨ瑙掕壊鍒楄〃(鍖呭惈琚巿鏉冪姸鎬�)
+ *
+ * @param userId 鐢ㄦ埛ID
+ * @return 瑙掕壊鍒楄〃
+ */
+ List<SysRoleVo> selectRolesAuthByUserId(Long userId);
+
+ /**
* 鏍规嵁鐢ㄦ埛ID鏌ヨ瑙掕壊鏉冮檺
*
* @param userId 鐢ㄦ埛ID
@@ -65,6 +73,14 @@
* @return 瑙掕壊瀵硅薄淇℃伅
*/
SysRoleVo selectRoleById(Long roleId);
+
+ /**
+ * 閫氳繃瑙掕壊ID涓叉煡璇㈣鑹�
+ *
+ * @param roleIds 瑙掕壊ID涓�
+ * @return 瑙掕壊鍒楄〃淇℃伅
+ */
+ List<SysRoleVo> selectRoleByIds(List<Long> roleIds);
/**
* 鏍¢獙瑙掕壊鍚嶇О鏄惁鍞竴
@@ -180,4 +196,5 @@
int insertAuthUsers(Long roleId, Long[] userIds);
void cleanOnlineUserByRole(Long roleId);
+
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysSocialService.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysSocialService.java
index d5702c9..cc7016e 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysSocialService.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysSocialService.java
@@ -21,7 +21,7 @@
/**
* 鏌ヨ绀句細鍖栧叧绯诲垪琛�
*/
- List<SysSocialVo> queryList();
+ List<SysSocialVo> queryList(SysSocialBo bo);
/**
* 鏌ヨ绀句細鍖栧叧绯诲垪琛�
@@ -45,9 +45,7 @@
/**
- * 鏍规嵁 authId 鏌ヨ SysSocial 琛ㄥ拰 SysUser 琛紝杩斿洖 SysSocialAuthResult 鏄犲皠鐨勫璞�
- * @param authId 璁よ瘉ID
- * @return SysSocial
+ * 鏍规嵁 authId 鏌ヨ
*/
List<SysSocialVo> selectByAuthId(String authId);
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysUserService.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysUserService.java
index bbe78be..0325a25 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysUserService.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/ISysUserService.java
@@ -3,6 +3,7 @@
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.system.domain.bo.SysUserBo;
+import org.dromara.system.domain.vo.SysUserExportVo;
import org.dromara.system.domain.vo.SysUserVo;
import java.util.List;
@@ -23,7 +24,7 @@
* @param user 鐢ㄦ埛淇℃伅
* @return 鐢ㄦ埛淇℃伅闆嗗悎淇℃伅
*/
- List<SysUserVo> selectUserList(SysUserBo user);
+ List<SysUserExportVo> selectUserExportList(SysUserBo user);
/**
* 鏍规嵁鏉′欢鍒嗛〉鏌ヨ宸插垎閰嶇敤鎴疯鑹插垪琛�
@@ -66,20 +67,29 @@
SysUserVo selectUserById(Long userId);
/**
+ * 閫氳繃鐢ㄦ埛ID涓叉煡璇㈢敤鎴�
+ *
+ * @param userIds 鐢ㄦ埛ID涓�
+ * @param deptId 閮ㄩ棬id
+ * @return 鐢ㄦ埛鍒楄〃淇℃伅
+ */
+ List<SysUserVo> selectUserByIds(List<Long> userIds, Long deptId);
+
+ /**
* 鏍规嵁鐢ㄦ埛ID鏌ヨ鐢ㄦ埛鎵�灞炶鑹茬粍
*
- * @param userName 鐢ㄦ埛鍚�
+ * @param userId 鐢ㄦ埛ID
* @return 缁撴灉
*/
- String selectUserRoleGroup(String userName);
+ String selectUserRoleGroup(Long userId);
/**
* 鏍规嵁鐢ㄦ埛ID鏌ヨ鐢ㄦ埛鎵�灞炲矖浣嶇粍
*
- * @param userName 鐢ㄦ埛鍚�
+ * @param userId 鐢ㄦ埛ID
* @return 缁撴灉
*/
- String selectUserPostGroup(String userName);
+ String selectUserPostGroup(Long userId);
/**
* 鏍¢獙鐢ㄦ埛鍚嶇О鏄惁鍞竴
@@ -205,8 +215,8 @@
/**
* 閫氳繃閮ㄩ棬id鏌ヨ褰撳墠閮ㄩ棬鎵�鏈夌敤鎴�
*
- * @param deptId
- * @return
+ * @param deptId 閮ㄩ棬id
+ * @return 缁撴灉
*/
List<SysUserVo> selectUserListByDept(Long deptId);
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysClientServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysClientServiceImpl.java
index aecaf66..26bc491 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysClientServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysClientServiceImpl.java
@@ -7,6 +7,7 @@
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
+import org.dromara.common.core.constant.CacheNames;
import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.PageQuery;
@@ -16,6 +17,8 @@
import org.dromara.system.domain.vo.SysClientVo;
import org.dromara.system.mapper.SysClientMapper;
import org.dromara.system.service.ISysClientService;
+import org.springframework.cache.annotation.CacheEvict;
+import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;
import java.util.Collection;
@@ -48,9 +51,10 @@
/**
* 鏌ヨ瀹㈡埛绔鐞�
*/
+ @Cacheable(cacheNames = CacheNames.SYS_CLIENT, key = "#clientId")
@Override
- public SysClient queryByClientId(String clientId) {
- return baseMapper.selectOne(new LambdaQueryWrapper<SysClient>().eq(SysClient::getClientId, clientId));
+ public SysClientVo queryByClientId(String clientId) {
+ return baseMapper.selectVoOne(new LambdaQueryWrapper<SysClient>().eq(SysClient::getClientId, clientId));
}
/**
@@ -105,6 +109,7 @@
/**
* 淇敼瀹㈡埛绔鐞�
*/
+ @CacheEvict(cacheNames = CacheNames.SYS_CLIENT, key = "#bo.clientId")
@Override
public Boolean updateByBo(SysClientBo bo) {
SysClient update = MapstructUtils.convert(bo, SysClient.class);
@@ -116,12 +121,13 @@
/**
* 淇敼鐘舵��
*/
+ @CacheEvict(cacheNames = CacheNames.SYS_CLIENT, key = "#clientId")
@Override
- public int updateUserStatus(Long id, String status) {
+ public int updateUserStatus(String clientId, String status) {
return baseMapper.update(null,
new LambdaUpdateWrapper<SysClient>()
.set(SysClient::getStatus, status)
- .eq(SysClient::getId, id));
+ .eq(SysClient::getClientId, clientId));
}
/**
@@ -134,6 +140,7 @@
/**
* 鎵归噺鍒犻櫎瀹㈡埛绔鐞�
*/
+ @CacheEvict(cacheNames = CacheNames.SYS_CLIENT, allEntries = true)
@Override
public Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid) {
if (isValid) {
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysConfigServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysConfigServiceImpl.java
index 7738d80..bebfdad 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysConfigServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysConfigServiceImpl.java
@@ -154,6 +154,7 @@
}
row = baseMapper.updateById(config);
} else {
+ CacheUtils.evict(CacheNames.SYS_CONFIG, config.getConfigKey());
row = baseMapper.update(config, new LambdaQueryWrapper<SysConfig>()
.eq(SysConfig::getConfigKey, config.getConfigKey()));
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDeptServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDeptServiceImpl.java
index fe5cc0e..cb3f340 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDeptServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDeptServiceImpl.java
@@ -7,6 +7,7 @@
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import lombok.RequiredArgsConstructor;
import org.dromara.common.core.constant.CacheNames;
import org.dromara.common.core.constant.UserConstants;
import org.dromara.common.core.exception.ServiceException;
@@ -27,7 +28,6 @@
import org.dromara.system.mapper.SysRoleMapper;
import org.dromara.system.mapper.SysUserMapper;
import org.dromara.system.service.ISysDeptService;
-import lombok.RequiredArgsConstructor;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;
@@ -82,7 +82,9 @@
lqw.eq(ObjectUtil.isNotNull(bo.getDeptId()), SysDept::getDeptId, bo.getDeptId());
lqw.eq(ObjectUtil.isNotNull(bo.getParentId()), SysDept::getParentId, bo.getParentId());
lqw.like(StringUtils.isNotBlank(bo.getDeptName()), SysDept::getDeptName, bo.getDeptName());
+ lqw.like(StringUtils.isNotBlank(bo.getDeptCategory()), SysDept::getDeptCategory, bo.getDeptCategory());
lqw.eq(StringUtils.isNotBlank(bo.getStatus()), SysDept::getStatus, bo.getStatus());
+ lqw.orderByAsc(SysDept::getAncestors);
lqw.orderByAsc(SysDept::getParentId);
lqw.orderByAsc(SysDept::getOrderNum);
lqw.orderByAsc(SysDept::getDeptId);
@@ -136,6 +138,14 @@
.select(SysDept::getDeptName).eq(SysDept::getDeptId, dept.getParentId()));
dept.setParentName(ObjectUtil.isNotNull(parentDept) ? parentDept.getDeptName() : null);
return dept;
+ }
+
+ @Override
+ public List<SysDeptVo> selectDeptByIds(List<Long> deptIds) {
+ return baseMapper.selectDeptList(new LambdaQueryWrapper<SysDept>()
+ .select(SysDept::getDeptId, SysDept::getDeptName, SysDept::getLeader)
+ .eq(SysDept::getStatus, UserConstants.DEPT_NORMAL)
+ .in(CollUtil.isNotEmpty(deptIds), SysDept::getDeptId, deptIds));
}
/**
@@ -209,6 +219,20 @@
}
/**
+ * 鏍¢獙閮ㄩ棬绫诲埆缂栫爜鏄惁鍞竴
+ *
+ * @param dept 閮ㄩ棬淇℃伅
+ * @return 缁撴灉
+ */
+ @Override
+ public boolean checkDeptCategoryUnique(SysDeptBo dept) {
+ boolean exist = baseMapper.exists(new LambdaQueryWrapper<SysDept>()
+ .eq(SysDept::getDeptCategory, dept.getDeptCategory())
+ .ne(ObjectUtil.isNotNull(dept.getDeptId()), SysDept::getDeptId, dept.getDeptId()));
+ return !exist;
+ }
+
+ /**
* 鏍¢獙閮ㄩ棬鏄惁鏈夋暟鎹潈闄�
*
* @param deptId 閮ㄩ棬id
@@ -221,8 +245,7 @@
if (LoginHelper.isSuperAdmin()) {
return;
}
- SysDeptVo dept = baseMapper.selectDeptById(deptId);
- if (ObjectUtil.isNull(dept)) {
+ if (baseMapper.countDeptById(deptId) == 0) {
throw new ServiceException("娌℃湁鏉冮檺璁块棶閮ㄩ棬鏁版嵁锛�");
}
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictDataServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictDataServiceImpl.java
index 74d4454..1ab0faf 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictDataServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictDataServiceImpl.java
@@ -1,5 +1,6 @@
package org.dromara.system.service.impl;
+import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
@@ -135,4 +136,21 @@
throw new ServiceException("鎿嶄綔澶辫触");
}
+ /**
+ * 鏍¢獙瀛楀吀閿�兼槸鍚﹀敮涓�
+ *
+ * @param dict 瀛楀吀鏁版嵁
+ * @return 缁撴灉
+ */
+ @Override
+ public boolean checkDictDataUnique(SysDictDataBo dict) {
+ Long dictCode = ObjectUtil.isNull(dict.getDictCode()) ? -1L : dict.getDictCode();
+ SysDictData entity = baseMapper.selectOne(new LambdaQueryWrapper<SysDictData>()
+ .eq(SysDictData::getDictType, dict.getDictType()).eq(SysDictData::getDictValue, dict.getDictValue()));
+ if (ObjectUtil.isNotNull(entity) && !dictCode.equals(entity.getDictCode())) {
+ return false;
+ }
+ return true;
+ }
+
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictTypeServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictTypeServiceImpl.java
index 346d6bc..bc6663f 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictTypeServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysDictTypeServiceImpl.java
@@ -1,13 +1,12 @@
package org.dromara.system.service.impl;
-import cn.dev33.satoken.context.SaHolder;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
-import org.dromara.common.core.constant.CacheConstants;
+import lombok.RequiredArgsConstructor;
import org.dromara.common.core.constant.CacheNames;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.service.DictService;
@@ -26,7 +25,6 @@
import org.dromara.system.mapper.SysDictDataMapper;
import org.dromara.system.mapper.SysDictTypeMapper;
import org.dromara.system.service.ISysDictTypeService;
-import lombok.RequiredArgsConstructor;
import org.springframework.cache.annotation.CachePut;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;
@@ -217,16 +215,9 @@
* @param separator 鍒嗛殧绗�
* @return 瀛楀吀鏍囩
*/
- @SuppressWarnings("unchecked cast")
@Override
public String getDictLabel(String dictType, String dictValue, String separator) {
- // 浼樺厛浠庢湰鍦扮紦瀛樿幏鍙�
- List<SysDictDataVo> datas = (List<SysDictDataVo>) SaHolder.getStorage().get(CacheConstants.SYS_DICT_KEY + dictType);
- if (ObjectUtil.isNull(datas)) {
- datas = SpringUtils.getAopProxy(this).selectDictDataByType(dictType);
- SaHolder.getStorage().set(CacheConstants.SYS_DICT_KEY + dictType, datas);
- }
-
+ List<SysDictDataVo> datas = SpringUtils.getAopProxy(this).selectDictDataByType(dictType);
Map<String, String> map = StreamUtils.toMap(datas, SysDictDataVo::getDictValue, SysDictDataVo::getDictLabel);
if (StringUtils.containsAny(dictValue, separator)) {
return Arrays.stream(dictValue.split(separator))
@@ -245,16 +236,9 @@
* @param separator 鍒嗛殧绗�
* @return 瀛楀吀鍊�
*/
- @SuppressWarnings("unchecked cast")
@Override
public String getDictValue(String dictType, String dictLabel, String separator) {
- // 浼樺厛浠庢湰鍦扮紦瀛樿幏鍙�
- List<SysDictDataVo> datas = (List<SysDictDataVo>) SaHolder.getStorage().get(CacheConstants.SYS_DICT_KEY + dictType);
- if (ObjectUtil.isNull(datas)) {
- datas = SpringUtils.getAopProxy(this).selectDictDataByType(dictType);
- SaHolder.getStorage().set(CacheConstants.SYS_DICT_KEY + dictType, datas);
- }
-
+ List<SysDictDataVo> datas = SpringUtils.getAopProxy(this).selectDictDataByType(dictType);
Map<String, String> map = StreamUtils.toMap(datas, SysDictDataVo::getDictLabel, SysDictDataVo::getDictValue);
if (StringUtils.containsAny(dictLabel, separator)) {
return Arrays.stream(dictLabel.split(separator))
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysLogininforServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysLogininforServiceImpl.java
index d215d59..9c930a0 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysLogininforServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysLogininforServiceImpl.java
@@ -5,30 +5,29 @@
import cn.hutool.http.useragent.UserAgentUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import jakarta.servlet.http.HttpServletRequest;
+import lombok.RequiredArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
import org.dromara.common.core.constant.Constants;
import org.dromara.common.core.utils.MapstructUtils;
-import org.dromara.common.mybatis.core.page.PageQuery;
-import org.dromara.common.log.event.LogininforEvent;
-import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.core.utils.ServletUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.core.utils.ip.AddressUtils;
+import org.dromara.common.log.event.LogininforEvent;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.satoken.utils.LoginHelper;
-import org.dromara.system.domain.SysClient;
import org.dromara.system.domain.SysLogininfor;
import org.dromara.system.domain.bo.SysLogininforBo;
+import org.dromara.system.domain.vo.SysClientVo;
import org.dromara.system.domain.vo.SysLogininforVo;
-import org.dromara.system.mapper.SysClientMapper;
import org.dromara.system.mapper.SysLogininforMapper;
import org.dromara.system.service.ISysClientService;
import org.dromara.system.service.ISysLogininforService;
-import lombok.RequiredArgsConstructor;
-import lombok.extern.slf4j.Slf4j;
import org.springframework.context.event.EventListener;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;
-import jakarta.servlet.http.HttpServletRequest;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
@@ -60,10 +59,10 @@
final UserAgent userAgent = UserAgentUtil.parse(request.getHeader("User-Agent"));
final String ip = ServletUtils.getClientIP(request);
// 瀹㈡埛绔俊鎭�
- String clientid = request.getHeader(LoginHelper.CLIENT_KEY);
- SysClient client = null;
- if (StringUtils.isNotBlank(clientid)) {
- client = clientService.queryByClientId(clientid);
+ String clientId = request.getHeader(LoginHelper.CLIENT_KEY);
+ SysClientVo client = null;
+ if (StringUtils.isNotBlank(clientId)) {
+ client = clientService.queryByClientId(clientId);
}
String address = AddressUtils.getRealAddressByIP(ip);
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysNoticeServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysNoticeServiceImpl.java
index 8e2b5ac..18b7a08 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysNoticeServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysNoticeServiceImpl.java
@@ -9,6 +9,7 @@
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.system.domain.SysNotice;
+import org.dromara.system.domain.SysUser;
import org.dromara.system.domain.bo.SysNoticeBo;
import org.dromara.system.domain.vo.SysNoticeVo;
import org.dromara.system.domain.vo.SysUserVo;
@@ -68,7 +69,7 @@
lqw.like(StringUtils.isNotBlank(bo.getNoticeTitle()), SysNotice::getNoticeTitle, bo.getNoticeTitle());
lqw.eq(StringUtils.isNotBlank(bo.getNoticeType()), SysNotice::getNoticeType, bo.getNoticeType());
if (StringUtils.isNotBlank(bo.getCreateByName())) {
- SysUserVo sysUser = userMapper.selectUserByUserName(bo.getCreateByName());
+ SysUserVo sysUser = userMapper.selectVoOne(new LambdaQueryWrapper<SysUser>().eq(SysUser::getUserName, bo.getCreateByName()));
lqw.eq(SysNotice::getCreateBy, ObjectUtil.isNotNull(sysUser) ? sysUser.getUserId() : null);
}
lqw.orderByAsc(SysNotice::getNoticeId);
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysOssServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysOssServiceImpl.java
index c7d4719..aa094b2 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysOssServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysOssServiceImpl.java
@@ -1,12 +1,15 @@
package org.dromara.system.service.impl;
+import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.convert.Convert;
-import cn.hutool.core.io.IoUtil;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import jakarta.servlet.http.HttpServletResponse;
+import lombok.RequiredArgsConstructor;
import org.dromara.common.core.constant.CacheNames;
+import org.dromara.common.core.domain.dto.OssDTO;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.service.OssService;
import org.dromara.common.core.utils.MapstructUtils;
@@ -25,8 +28,6 @@
import org.dromara.system.domain.vo.SysOssVo;
import org.dromara.system.mapper.SysOssMapper;
import org.dromara.system.service.ISysOssService;
-import jakarta.servlet.http.HttpServletResponse;
-import lombok.RequiredArgsConstructor;
import org.jetbrains.annotations.NotNull;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.http.MediaType;
@@ -35,8 +36,10 @@
import java.io.File;
import java.io.IOException;
-import java.io.InputStream;
-import java.util.*;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
/**
* 鏂囦欢涓婁紶 鏈嶅姟灞傚疄鐜�
@@ -49,6 +52,13 @@
private final SysOssMapper baseMapper;
+ /**
+ * 鏌ヨOSS瀵硅薄瀛樺偍鍒楄〃
+ *
+ * @param bo OSS瀵硅薄瀛樺偍鍒嗛〉鏌ヨ瀵硅薄
+ * @param pageQuery 鍒嗛〉鏌ヨ瀹炰綋绫�
+ * @return 缁撴灉
+ */
@Override
public TableDataInfo<SysOssVo> queryPageList(SysOssBo bo, PageQuery pageQuery) {
LambdaQueryWrapper<SysOss> lqw = buildQueryWrapper(bo);
@@ -58,6 +68,12 @@
return TableDataInfo.build(result);
}
+ /**
+ * 鏍规嵁涓�缁� ossIds 鑾峰彇瀵瑰簲鐨� SysOssVo 鍒楄〃
+ *
+ * @param ossIds 涓�缁勬枃浠跺湪鏁版嵁搴撲腑鐨勫敮涓�鏍囪瘑闆嗗悎
+ * @return 鍖呭惈 SysOssVo 瀵硅薄鐨勫垪琛�
+ */
@Override
public List<SysOssVo> listByIds(Collection<Long> ossIds) {
List<SysOssVo> list = new ArrayList<>();
@@ -75,6 +91,12 @@
return list;
}
+ /**
+ * 鏍规嵁涓�缁� ossIds 鑾峰彇瀵瑰簲鏂囦欢鐨� URL 鍒楄〃
+ *
+ * @param ossIds 浠ラ�楀彿鍒嗛殧鐨� ossId 瀛楃涓�
+ * @return 浠ラ�楀彿鍒嗛殧鐨勬枃浠� URL 瀛楃涓�
+ */
@Override
public String selectUrlByIds(String ossIds) {
List<String> list = new ArrayList<>();
@@ -92,6 +114,24 @@
return String.join(StringUtils.SEPARATOR, list);
}
+ @Override
+ public List<OssDTO> selectByIds(String ossIds) {
+ List<OssDTO> list = new ArrayList<>();
+ for (Long id : StringUtils.splitTo(ossIds, Convert::toLong)) {
+ SysOssVo vo = SpringUtils.getAopProxy(this).getById(id);
+ if (ObjectUtil.isNotNull(vo)) {
+ try {
+ vo.setUrl(this.matchingUrl(vo).getUrl());
+ list.add(BeanUtil.toBean(vo, OssDTO.class));
+ } catch (Exception ignored) {
+ // 濡傛灉oss寮傚父鏃犳硶杩炴帴鍒欏皢鏁版嵁鐩存帴杩斿洖
+ list.add(BeanUtil.toBean(vo, OssDTO.class));
+ }
+ }
+ }
+ return list;
+ }
+
private LambdaQueryWrapper<SysOss> buildQueryWrapper(SysOssBo bo) {
Map<String, Object> params = bo.getParams();
LambdaQueryWrapper<SysOss> lqw = Wrappers.lambdaQuery();
@@ -107,12 +147,25 @@
return lqw;
}
+ /**
+ * 鏍规嵁 ossId 浠庣紦瀛樻垨鏁版嵁搴撲腑鑾峰彇 SysOssVo 瀵硅薄
+ *
+ * @param ossId 鏂囦欢鍦ㄦ暟鎹簱涓殑鍞竴鏍囪瘑
+ * @return SysOssVo 瀵硅薄锛屽寘鍚枃浠朵俊鎭�
+ */
@Cacheable(cacheNames = CacheNames.SYS_OSS, key = "#ossId")
@Override
public SysOssVo getById(Long ossId) {
return baseMapper.selectVoById(ossId);
}
+
+ /**
+ * 鏂囦欢涓嬭浇鏂规硶锛屾敮鎸佷竴娆℃�т笅杞藉畬鏁存枃浠�
+ *
+ * @param ossId OSS瀵硅薄ID
+ * @param response HttpServletResponse瀵硅薄锛岀敤浜庤缃搷搴斿ご鍜屽悜瀹㈡埛绔彂閫佹枃浠跺唴瀹�
+ */
@Override
public void download(Long ossId, HttpServletResponse response) throws IOException {
SysOssVo sysOss = SpringUtils.getAopProxy(this).getById(ossId);
@@ -122,15 +175,17 @@
FileUtils.setAttachmentResponseHeader(response, sysOss.getOriginalName());
response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE + "; charset=UTF-8");
OssClient storage = OssFactory.instance(sysOss.getService());
- try(InputStream inputStream = storage.getObjectContent(sysOss.getUrl())) {
- int available = inputStream.available();
- IoUtil.copy(inputStream, response.getOutputStream(), available);
- response.setContentLength(available);
- } catch (Exception e) {
- throw new ServiceException(e.getMessage());
- }
+ long contentLength = storage.download(sysOss.getFileName(), response.getOutputStream());
+ response.setContentLengthLong(contentLength);
}
+ /**
+ * 涓婁紶 MultipartFile 鍒板璞″瓨鍌ㄦ湇鍔★紝骞朵繚瀛樻枃浠朵俊鎭埌鏁版嵁搴�
+ *
+ * @param file 瑕佷笂浼犵殑 MultipartFile 瀵硅薄
+ * @return 涓婁紶鎴愬姛鍚庣殑 SysOssVo 瀵硅薄锛屽寘鍚枃浠朵俊鎭�
+ * @throws ServiceException 濡傛灉涓婁紶杩囩▼涓彂鐢熷紓甯革紝鍒欐姏鍑� ServiceException 寮傚父
+ */
@Override
public SysOssVo upload(MultipartFile file) {
String originalfileName = file.getOriginalFilename();
@@ -138,7 +193,7 @@
OssClient storage = OssFactory.instance();
UploadResult uploadResult;
try {
- uploadResult = storage.uploadSuffix(file.getBytes(), suffix, file.getContentType());
+ uploadResult = storage.uploadSuffix(file.getBytes(), suffix);
} catch (IOException e) {
throw new ServiceException(e.getMessage());
}
@@ -146,6 +201,12 @@
return buildResultEntity(originalfileName, suffix, storage.getConfigKey(), uploadResult);
}
+ /**
+ * 涓婁紶鏂囦欢鍒板璞″瓨鍌ㄦ湇鍔★紝骞朵繚瀛樻枃浠朵俊鎭埌鏁版嵁搴�
+ *
+ * @param file 瑕佷笂浼犵殑鏂囦欢瀵硅薄
+ * @return 涓婁紶鎴愬姛鍚庣殑 SysOssVo 瀵硅薄锛屽寘鍚枃浠朵俊鎭�
+ */
@Override
public SysOssVo upload(File file) {
String originalfileName = file.getName();
@@ -169,6 +230,13 @@
return this.matchingUrl(sysOssVo);
}
+ /**
+ * 鍒犻櫎OSS瀵硅薄瀛樺偍
+ *
+ * @param ids OSS瀵硅薄ID涓�
+ * @param isValid 鍒ゆ柇鏄惁闇�瑕佹牎楠�
+ * @return 缁撴灉
+ */
@Override
public Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid) {
if (isValid) {
@@ -183,7 +251,7 @@
}
/**
- * 鍖归厤Url
+ * 妗剁被鍨嬩负 private 鐨刄RL 淇敼涓轰复鏃禪RL鏃堕暱涓�120s
*
* @param oss OSS瀵硅薄
* @return oss 鍖归厤Url鐨凮SS瀵硅薄
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysPostServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysPostServiceImpl.java
index b69a06c..17cd5ca 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysPostServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysPostServiceImpl.java
@@ -1,27 +1,33 @@
package org.dromara.system.service.impl;
+import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
-import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.constant.UserConstants;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.utils.MapstructUtils;
+import org.dromara.common.core.utils.StreamUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.mybatis.helper.DataBaseHelper;
+import org.dromara.system.domain.SysDept;
import org.dromara.system.domain.SysPost;
import org.dromara.system.domain.SysUserPost;
import org.dromara.system.domain.bo.SysPostBo;
import org.dromara.system.domain.vo.SysPostVo;
+import org.dromara.system.mapper.SysDeptMapper;
import org.dromara.system.mapper.SysPostMapper;
import org.dromara.system.mapper.SysUserPostMapper;
import org.dromara.system.service.ISysPostService;
-import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import java.util.Arrays;
import java.util.List;
+import java.util.stream.Collectors;
/**
* 宀椾綅淇℃伅 鏈嶅姟灞傚鐞�
@@ -33,12 +39,12 @@
public class SysPostServiceImpl implements ISysPostService {
private final SysPostMapper baseMapper;
+ private final SysDeptMapper deptMapper;
private final SysUserPostMapper userPostMapper;
@Override
public TableDataInfo<SysPostVo> selectPagePostList(SysPostBo post, PageQuery pageQuery) {
- LambdaQueryWrapper<SysPost> lqw = buildQueryWrapper(post);
- Page<SysPostVo> page = baseMapper.selectVoPage(pageQuery.build(), lqw);
+ Page<SysPostVo> page = baseMapper.selectPagePostList(pageQuery.build(), buildQueryWrapper(post));
return TableDataInfo.build(page);
}
@@ -50,17 +56,39 @@
*/
@Override
public List<SysPostVo> selectPostList(SysPostBo post) {
- LambdaQueryWrapper<SysPost> lqw = buildQueryWrapper(post);
- return baseMapper.selectVoList(lqw);
+ return baseMapper.selectVoList(buildQueryWrapper(post));
}
+ /**
+ * 鏍规嵁鏌ヨ鏉′欢鏋勫缓鏌ヨ鍖呰鍣�
+ *
+ * @param bo 鏌ヨ鏉′欢瀵硅薄
+ * @return 鏋勫缓濂界殑鏌ヨ鍖呰鍣�
+ */
private LambdaQueryWrapper<SysPost> buildQueryWrapper(SysPostBo bo) {
- LambdaQueryWrapper<SysPost> lqw = Wrappers.lambdaQuery();
- lqw.like(StringUtils.isNotBlank(bo.getPostCode()), SysPost::getPostCode, bo.getPostCode());
- lqw.like(StringUtils.isNotBlank(bo.getPostName()), SysPost::getPostName, bo.getPostName());
- lqw.eq(StringUtils.isNotBlank(bo.getStatus()), SysPost::getStatus, bo.getStatus());
- lqw.orderByAsc(SysPost::getPostSort);
- return lqw;
+ LambdaQueryWrapper<SysPost> wrapper = new LambdaQueryWrapper<>();
+ wrapper.like(StringUtils.isNotBlank(bo.getPostCode()), SysPost::getPostCode, bo.getPostCode())
+ .like(StringUtils.isNotBlank(bo.getPostCategory()), SysPost::getPostCategory, bo.getPostCategory())
+ .like(StringUtils.isNotBlank(bo.getPostName()), SysPost::getPostName, bo.getPostName())
+ .eq(StringUtils.isNotBlank(bo.getStatus()), SysPost::getStatus, bo.getStatus())
+ .orderByAsc(SysPost::getPostSort);
+ if (ObjectUtil.isNotNull(bo.getDeptId())) {
+ //浼樺厛鍗曢儴闂ㄦ悳绱�
+ wrapper.eq(SysPost::getDeptId, bo.getDeptId());
+ } else if (ObjectUtil.isNotNull(bo.getBelongDeptId())) {
+ //閮ㄩ棬鏍戞悳绱�
+ wrapper.and(x -> {
+ List<Long> deptIds = deptMapper.selectList(new LambdaQueryWrapper<SysDept>()
+ .select(SysDept::getDeptId)
+ .apply(DataBaseHelper.findInSet(bo.getBelongDeptId(), "ancestors")))
+ .stream()
+ .map(SysDept::getDeptId)
+ .collect(Collectors.toList());
+ deptIds.add(bo.getBelongDeptId());
+ x.in(SysPost::getDeptId, deptIds);
+ });
+ }
+ return wrapper;
}
/**
@@ -92,7 +120,22 @@
*/
@Override
public List<Long> selectPostListByUserId(Long userId) {
- return baseMapper.selectPostListByUserId(userId);
+ List<SysPostVo> list = baseMapper.selectPostsByUserId(userId);
+ return StreamUtils.toList(list, SysPostVo::getPostId);
+ }
+
+ /**
+ * 閫氳繃宀椾綅ID涓叉煡璇㈠矖浣�
+ *
+ * @param postIds 宀椾綅id涓�
+ * @return 宀椾綅鍒楄〃淇℃伅
+ */
+ @Override
+ public List<SysPostVo> selectPostByIds(List<Long> postIds) {
+ return baseMapper.selectVoList(new LambdaQueryWrapper<SysPost>()
+ .select(SysPost::getPostId, SysPost::getPostName, SysPost::getPostCode)
+ .eq(SysPost::getStatus, UserConstants.POST_NORMAL)
+ .in(CollUtil.isNotEmpty(postIds), SysPost::getPostId, postIds));
}
/**
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysRoleServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysRoleServiceImpl.java
index 8a2b939..abd294f 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysRoleServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysRoleServiceImpl.java
@@ -80,7 +80,6 @@
.between(params.get("beginTime") != null && params.get("endTime") != null,
"r.create_time", params.get("beginTime"), params.get("endTime"))
.orderByAsc("r.role_sort").orderByAsc("r.create_time");
- ;
return wrapper;
}
@@ -92,6 +91,17 @@
*/
@Override
public List<SysRoleVo> selectRolesByUserId(Long userId) {
+ return baseMapper.selectRolesByUserId(userId);
+ }
+
+ /**
+ * 鏍规嵁鐢ㄦ埛ID鏌ヨ瑙掕壊鍒楄〃(鍖呭惈琚巿鏉冪姸鎬�)
+ *
+ * @param userId 鐢ㄦ埛ID
+ * @return 瑙掕壊鍒楄〃
+ */
+ @Override
+ public List<SysRoleVo> selectRolesAuthByUserId(Long userId) {
List<SysRoleVo> userRoles = baseMapper.selectRolePermissionByUserId(userId);
List<SysRoleVo> roles = selectRoleAll();
for (SysRoleVo role : roles) {
@@ -141,7 +151,8 @@
*/
@Override
public List<Long> selectRoleListByUserId(Long userId) {
- return baseMapper.selectRoleListByUserId(userId);
+ List<SysRoleVo> list = baseMapper.selectRolesByUserId(userId);
+ return StreamUtils.toList(list, SysRoleVo::getRoleId);
}
/**
@@ -156,6 +167,19 @@
}
/**
+ * 閫氳繃瑙掕壊ID涓叉煡璇㈣鑹�
+ *
+ * @param roleIds 瑙掕壊ID涓�
+ * @return 瑙掕壊鍒楄〃淇℃伅
+ */
+ @Override
+ public List<SysRoleVo> selectRoleByIds(List<Long> roleIds) {
+ return baseMapper.selectRoleList(new QueryWrapper<SysRole>()
+ .eq("r.status", UserConstants.ROLE_NORMAL)
+ .in(CollUtil.isNotEmpty(roleIds), "r.role_id", roleIds));
+ }
+
+ /**
* 鏍¢獙瑙掕壊鍚嶇О鏄惁鍞竴
*
* @param role 瑙掕壊淇℃伅
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysSocialServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysSocialServiceImpl.java
index aa86ae1..9c54cbc 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysSocialServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysSocialServiceImpl.java
@@ -1,8 +1,10 @@
package org.dromara.system.service.impl;
+import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import lombok.RequiredArgsConstructor;
import org.dromara.common.core.utils.MapstructUtils;
+import org.dromara.common.core.utils.StringUtils;
import org.dromara.system.domain.SysSocial;
import org.dromara.system.domain.bo.SysSocialBo;
import org.dromara.system.domain.vo.SysSocialVo;
@@ -37,8 +39,12 @@
* 鎺堟潈鍒楄〃
*/
@Override
- public List<SysSocialVo> queryList() {
- return baseMapper.selectVoList();
+ public List<SysSocialVo> queryList(SysSocialBo bo) {
+ LambdaQueryWrapper<SysSocial> lqw = new LambdaQueryWrapper<SysSocial>()
+ .eq(ObjectUtil.isNotNull(bo.getUserId()), SysSocial::getUserId, bo.getUserId())
+ .eq(StringUtils.isNotBlank(bo.getAuthId()), SysSocial::getAuthId, bo.getAuthId())
+ .eq(StringUtils.isNotBlank(bo.getSource()), SysSocial::getSource, bo.getSource());
+ return baseMapper.selectVoList(lqw);
}
@Override
diff --git a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysUserServiceImpl.java b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysUserServiceImpl.java
index 7ee19e8..93f1cc7 100644
--- a/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysUserServiceImpl.java
+++ b/ruoyi-modules/ruoyi-system/src/main/java/org/dromara/system/service/impl/SysUserServiceImpl.java
@@ -1,6 +1,8 @@
package org.dromara.system.service.impl;
+import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.convert.Convert;
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.Wrapper;
@@ -13,9 +15,11 @@
import lombok.extern.slf4j.Slf4j;
import org.dromara.common.core.constant.CacheNames;
import org.dromara.common.core.constant.UserConstants;
+import org.dromara.common.core.domain.dto.UserDTO;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.service.UserService;
import org.dromara.common.core.utils.MapstructUtils;
+import org.dromara.common.core.utils.SpringUtils;
import org.dromara.common.core.utils.StreamUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.PageQuery;
@@ -29,6 +33,7 @@
import org.dromara.system.domain.bo.SysUserBo;
import org.dromara.system.domain.vo.SysPostVo;
import org.dromara.system.domain.vo.SysRoleVo;
+import org.dromara.system.domain.vo.SysUserExportVo;
import org.dromara.system.domain.vo.SysUserVo;
import org.dromara.system.mapper.*;
import org.dromara.system.service.ISysUserService;
@@ -36,6 +41,7 @@
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
+import java.util.ArrayList;
import java.util.List;
import java.util.Map;
@@ -69,28 +75,31 @@
* @return 鐢ㄦ埛淇℃伅闆嗗悎淇℃伅
*/
@Override
- public List<SysUserVo> selectUserList(SysUserBo user) {
- return baseMapper.selectUserList(this.buildQueryWrapper(user));
+ public List<SysUserExportVo> selectUserExportList(SysUserBo user) {
+ return baseMapper.selectUserExportList(this.buildQueryWrapper(user));
}
private Wrapper<SysUser> buildQueryWrapper(SysUserBo user) {
Map<String, Object> params = user.getParams();
QueryWrapper<SysUser> wrapper = Wrappers.query();
wrapper.eq("u.del_flag", UserConstants.USER_NORMAL)
- .eq(ObjectUtil.isNotNull(user.getUserId()), "u.user_id", user.getUserId())
- .like(StringUtils.isNotBlank(user.getUserName()), "u.user_name", user.getUserName())
- .eq(StringUtils.isNotBlank(user.getStatus()), "u.status", user.getStatus())
- .like(StringUtils.isNotBlank(user.getPhonenumber()), "u.phonenumber", user.getPhonenumber())
- .between(params.get("beginTime") != null && params.get("endTime") != null,
- "u.create_time", params.get("beginTime"), params.get("endTime"))
- .and(ObjectUtil.isNotNull(user.getDeptId()), w -> {
- List<SysDept> deptList = deptMapper.selectList(new LambdaQueryWrapper<SysDept>()
- .select(SysDept::getDeptId)
- .apply(DataBaseHelper.findInSet(user.getDeptId(), "ancestors")));
- List<Long> ids = StreamUtils.toList(deptList, SysDept::getDeptId);
- ids.add(user.getDeptId());
- w.in("u.dept_id", ids);
- }).orderByAsc("u.user_id");
+ .eq(ObjectUtil.isNotNull(user.getUserId()), "u.user_id", user.getUserId())
+ .like(StringUtils.isNotBlank(user.getUserName()), "u.user_name", user.getUserName())
+ .eq(StringUtils.isNotBlank(user.getStatus()), "u.status", user.getStatus())
+ .like(StringUtils.isNotBlank(user.getPhonenumber()), "u.phonenumber", user.getPhonenumber())
+ .between(params.get("beginTime") != null && params.get("endTime") != null,
+ "u.create_time", params.get("beginTime"), params.get("endTime"))
+ .and(ObjectUtil.isNotNull(user.getDeptId()), w -> {
+ List<SysDept> deptList = deptMapper.selectList(new LambdaQueryWrapper<SysDept>()
+ .select(SysDept::getDeptId)
+ .apply(DataBaseHelper.findInSet(user.getDeptId(), "ancestors")));
+ List<Long> ids = StreamUtils.toList(deptList, SysDept::getDeptId);
+ ids.add(user.getDeptId());
+ w.in("u.dept_id", ids);
+ }).orderByAsc("u.user_id");
+ if (StringUtils.isNotBlank(user.getExcludeUserIds())) {
+ wrapper.notIn("u.user_id", StringUtils.splitList(user.getExcludeUserIds()));
+ }
return wrapper;
}
@@ -104,11 +113,11 @@
public TableDataInfo<SysUserVo> selectAllocatedList(SysUserBo user, PageQuery pageQuery) {
QueryWrapper<SysUser> wrapper = Wrappers.query();
wrapper.eq("u.del_flag", UserConstants.USER_NORMAL)
- .eq(ObjectUtil.isNotNull(user.getRoleId()), "r.role_id", user.getRoleId())
- .like(StringUtils.isNotBlank(user.getUserName()), "u.user_name", user.getUserName())
- .eq(StringUtils.isNotBlank(user.getStatus()), "u.status", user.getStatus())
- .like(StringUtils.isNotBlank(user.getPhonenumber()), "u.phonenumber", user.getPhonenumber())
- .orderByAsc("u.user_id");
+ .eq(ObjectUtil.isNotNull(user.getRoleId()), "r.role_id", user.getRoleId())
+ .like(StringUtils.isNotBlank(user.getUserName()), "u.user_name", user.getUserName())
+ .eq(StringUtils.isNotBlank(user.getStatus()), "u.status", user.getStatus())
+ .like(StringUtils.isNotBlank(user.getPhonenumber()), "u.phonenumber", user.getPhonenumber())
+ .orderByAsc("u.user_id");
Page<SysUserVo> page = baseMapper.selectAllocatedList(pageQuery.build(), wrapper);
return TableDataInfo.build(page);
}
@@ -124,11 +133,11 @@
List<Long> userIds = userRoleMapper.selectUserIdsByRoleId(user.getRoleId());
QueryWrapper<SysUser> wrapper = Wrappers.query();
wrapper.eq("u.del_flag", UserConstants.USER_NORMAL)
- .and(w -> w.ne("r.role_id", user.getRoleId()).or().isNull("r.role_id"))
- .notIn(CollUtil.isNotEmpty(userIds), "u.user_id", userIds)
- .like(StringUtils.isNotBlank(user.getUserName()), "u.user_name", user.getUserName())
- .like(StringUtils.isNotBlank(user.getPhonenumber()), "u.phonenumber", user.getPhonenumber())
- .orderByAsc("u.user_id");
+ .and(w -> w.ne("r.role_id", user.getRoleId()).or().isNull("r.role_id"))
+ .notIn(CollUtil.isNotEmpty(userIds), "u.user_id", userIds)
+ .like(StringUtils.isNotBlank(user.getUserName()), "u.user_name", user.getUserName())
+ .like(StringUtils.isNotBlank(user.getPhonenumber()), "u.phonenumber", user.getPhonenumber())
+ .orderByAsc("u.user_id");
Page<SysUserVo> page = baseMapper.selectUnallocatedList(pageQuery.build(), wrapper);
return TableDataInfo.build(page);
}
@@ -141,7 +150,7 @@
*/
@Override
public SysUserVo selectUserByUserName(String userName) {
- return baseMapper.selectUserByUserName(userName);
+ return baseMapper.selectVoOne(new LambdaQueryWrapper<SysUser>().eq(SysUser::getUserName, userName));
}
/**
@@ -152,7 +161,7 @@
*/
@Override
public SysUserVo selectUserByPhonenumber(String phonenumber) {
- return baseMapper.selectUserByPhonenumber(phonenumber);
+ return baseMapper.selectVoOne(new LambdaQueryWrapper<SysUser>().eq(SysUser::getPhonenumber, phonenumber));
}
/**
@@ -163,18 +172,39 @@
*/
@Override
public SysUserVo selectUserById(Long userId) {
- return baseMapper.selectUserById(userId);
+ SysUserVo user = baseMapper.selectVoById(userId);
+ if (ObjectUtil.isNull(user)) {
+ return user;
+ }
+ user.setRoles(roleMapper.selectRolesByUserId(user.getUserId()));
+ return user;
+ }
+
+ /**
+ * 閫氳繃鐢ㄦ埛ID涓叉煡璇㈢敤鎴�
+ *
+ * @param userIds 鐢ㄦ埛ID涓�
+ * @param deptId 閮ㄩ棬id
+ * @return 鐢ㄦ埛鍒楄〃淇℃伅
+ */
+ @Override
+ public List<SysUserVo> selectUserByIds(List<Long> userIds, Long deptId) {
+ return baseMapper.selectUserList(new LambdaQueryWrapper<SysUser>()
+ .select(SysUser::getUserId, SysUser::getUserName, SysUser::getNickName)
+ .eq(SysUser::getStatus, UserConstants.USER_NORMAL)
+ .eq(ObjectUtil.isNotNull(deptId), SysUser::getDeptId, deptId)
+ .in(CollUtil.isNotEmpty(userIds), SysUser::getUserId, userIds));
}
/**
* 鏌ヨ鐢ㄦ埛鎵�灞炶鑹茬粍
*
- * @param userName 鐢ㄦ埛鍚�
+ * @param userId 鐢ㄦ埛ID
* @return 缁撴灉
*/
@Override
- public String selectUserRoleGroup(String userName) {
- List<SysRoleVo> list = roleMapper.selectRolesByUserName(userName);
+ public String selectUserRoleGroup(Long userId) {
+ List<SysRoleVo> list = roleMapper.selectRolesByUserId(userId);
if (CollUtil.isEmpty(list)) {
return StringUtils.EMPTY;
}
@@ -184,12 +214,12 @@
/**
* 鏌ヨ鐢ㄦ埛鎵�灞炲矖浣嶇粍
*
- * @param userName 鐢ㄦ埛鍚�
+ * @param userId 鐢ㄦ埛ID
* @return 缁撴灉
*/
@Override
- public String selectUserPostGroup(String userName) {
- List<SysPostVo> list = postMapper.selectPostsByUserName(userName);
+ public String selectUserPostGroup(Long userId) {
+ List<SysPostVo> list = postMapper.selectPostsByUserId(userId);
if (CollUtil.isEmpty(list)) {
return StringUtils.EMPTY;
}
@@ -205,8 +235,8 @@
@Override
public boolean checkUserNameUnique(SysUserBo user) {
boolean exist = baseMapper.exists(new LambdaQueryWrapper<SysUser>()
- .eq(SysUser::getUserName, user.getUserName())
- .ne(ObjectUtil.isNotNull(user.getUserId()), SysUser::getUserId, user.getUserId()));
+ .eq(SysUser::getUserName, user.getUserName())
+ .ne(ObjectUtil.isNotNull(user.getUserId()), SysUser::getUserId, user.getUserId()));
return !exist;
}
@@ -218,8 +248,8 @@
@Override
public boolean checkPhoneUnique(SysUserBo user) {
boolean exist = baseMapper.exists(new LambdaQueryWrapper<SysUser>()
- .eq(SysUser::getPhonenumber, user.getPhonenumber())
- .ne(ObjectUtil.isNotNull(user.getUserId()), SysUser::getUserId, user.getUserId()));
+ .eq(SysUser::getPhonenumber, user.getPhonenumber())
+ .ne(ObjectUtil.isNotNull(user.getUserId()), SysUser::getUserId, user.getUserId()));
return !exist;
}
@@ -231,8 +261,8 @@
@Override
public boolean checkEmailUnique(SysUserBo user) {
boolean exist = baseMapper.exists(new LambdaQueryWrapper<SysUser>()
- .eq(SysUser::getEmail, user.getEmail())
- .ne(ObjectUtil.isNotNull(user.getUserId()), SysUser::getUserId, user.getUserId()));
+ .eq(SysUser::getEmail, user.getEmail())
+ .ne(ObjectUtil.isNotNull(user.getUserId()), SysUser::getUserId, user.getUserId()));
return !exist;
}
@@ -261,7 +291,7 @@
if (LoginHelper.isSuperAdmin()) {
return;
}
- if (ObjectUtil.isNull(baseMapper.selectUserById(userId))) {
+ if (baseMapper.countUserById(userId) == 0) {
throw new ServiceException("娌℃湁鏉冮檺璁块棶鐢ㄦ埛鏁版嵁锛�");
}
}
@@ -294,8 +324,8 @@
*/
@Override
public boolean registerUser(SysUserBo user, String tenantId) {
- user.setCreateBy(user.getUserId());
- user.setUpdateBy(user.getUserId());
+ user.setCreateBy(0L);
+ user.setUpdateBy(0L);
SysUser sysUser = MapstructUtils.convert(user, SysUser.class);
sysUser.setTenantId(tenantId);
return baseMapper.insert(sysUser) > 0;
@@ -345,9 +375,9 @@
@Override
public int updateUserStatus(Long userId, String status) {
return baseMapper.update(null,
- new LambdaUpdateWrapper<SysUser>()
- .set(SysUser::getStatus, status)
- .eq(SysUser::getUserId, userId));
+ new LambdaUpdateWrapper<SysUser>()
+ .set(SysUser::getStatus, status)
+ .eq(SysUser::getUserId, userId));
}
/**
@@ -359,12 +389,12 @@
@Override
public int updateUserProfile(SysUserBo user) {
return baseMapper.update(null,
- new LambdaUpdateWrapper<SysUser>()
- .set(ObjectUtil.isNotNull(user.getNickName()), SysUser::getNickName, user.getNickName())
- .set(SysUser::getPhonenumber, user.getPhonenumber())
- .set(SysUser::getEmail, user.getEmail())
- .set(SysUser::getSex, user.getSex())
- .eq(SysUser::getUserId, user.getUserId()));
+ new LambdaUpdateWrapper<SysUser>()
+ .set(ObjectUtil.isNotNull(user.getNickName()), SysUser::getNickName, user.getNickName())
+ .set(SysUser::getPhonenumber, user.getPhonenumber())
+ .set(SysUser::getEmail, user.getEmail())
+ .set(SysUser::getSex, user.getSex())
+ .eq(SysUser::getUserId, user.getUserId()));
}
/**
@@ -377,9 +407,9 @@
@Override
public boolean updateUserAvatar(Long userId, Long avatar) {
return baseMapper.update(null,
- new LambdaUpdateWrapper<SysUser>()
- .set(SysUser::getAvatar, avatar)
- .eq(SysUser::getUserId, userId)) > 0;
+ new LambdaUpdateWrapper<SysUser>()
+ .set(SysUser::getAvatar, avatar)
+ .eq(SysUser::getUserId, userId)) > 0;
}
/**
@@ -392,9 +422,9 @@
@Override
public int resetUserPwd(Long userId, String password) {
return baseMapper.update(null,
- new LambdaUpdateWrapper<SysUser>()
- .set(SysUser::getPassword, password)
- .eq(SysUser::getUserId, userId));
+ new LambdaUpdateWrapper<SysUser>()
+ .set(SysUser::getPassword, password)
+ .eq(SysUser::getUserId, userId));
}
/**
@@ -518,8 +548,8 @@
/**
* 閫氳繃閮ㄩ棬id鏌ヨ褰撳墠閮ㄩ棬鎵�鏈夌敤鎴�
*
- * @param deptId
- * @return
+ * @param deptId 閮ㄩ棬ID
+ * @return 鐢ㄦ埛淇℃伅闆嗗悎淇℃伅
*/
@Override
public List<SysUserVo> selectUserListByDept(Long deptId) {
@@ -529,14 +559,26 @@
return baseMapper.selectVoList(lqw);
}
+ /**
+ * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛璐︽埛
+ *
+ * @param userId 鐢ㄦ埛ID
+ * @return 鐢ㄦ埛璐︽埛
+ */
@Cacheable(cacheNames = CacheNames.SYS_USER_NAME, key = "#userId")
@Override
public String selectUserNameById(Long userId) {
SysUser sysUser = baseMapper.selectOne(new LambdaQueryWrapper<SysUser>()
- .select(SysUser::getUserName).eq(SysUser::getUserId, userId));
+ .select(SysUser::getUserName).eq(SysUser::getUserId, userId));
return ObjectUtil.isNull(sysUser) ? null : sysUser.getUserName();
}
+ /**
+ * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛璐︽埛
+ *
+ * @param userId 鐢ㄦ埛ID
+ * @return 鐢ㄦ埛璐︽埛
+ */
@Override
@Cacheable(cacheNames = CacheNames.SYS_NICKNAME, key = "#userId")
public String selectNicknameById(Long userId) {
@@ -544,4 +586,65 @@
.select(SysUser::getNickName).eq(SysUser::getUserId, userId));
return ObjectUtil.isNull(sysUser) ? null : sysUser.getNickName();
}
+
+ /**
+ * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛璐︽埛
+ *
+ * @param userIds 鐢ㄦ埛ID 澶氫釜鐢ㄩ�楀彿闅斿紑
+ * @return 鐢ㄦ埛璐︽埛
+ */
+ @Override
+ public String selectNicknameByIds(String userIds) {
+ List<String> list = new ArrayList<>();
+ for (Long id : StringUtils.splitTo(userIds, Convert::toLong)) {
+ String nickname = SpringUtils.getAopProxy(this).selectNicknameById(id);
+ if (StringUtils.isNotBlank(nickname)) {
+ list.add(nickname);
+ }
+ }
+ return String.join(StringUtils.SEPARATOR, list);
+ }
+
+ /**
+ * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛鎵嬫満鍙�
+ *
+ * @param userId 鐢ㄦ埛id
+ * @return 鐢ㄦ埛鎵嬫満鍙�
+ */
+ @Override
+ public String selectPhonenumberById(Long userId) {
+ SysUser sysUser = baseMapper.selectOne(new LambdaQueryWrapper<SysUser>()
+ .select(SysUser::getPhonenumber).eq(SysUser::getUserId, userId));
+ return ObjectUtil.isNull(sysUser) ? null : sysUser.getPhonenumber();
+ }
+
+ /**
+ * 閫氳繃鐢ㄦ埛ID鏌ヨ鐢ㄦ埛閭
+ *
+ * @param userId 鐢ㄦ埛id
+ * @return 鐢ㄦ埛閭
+ */
+ @Override
+ public String selectEmailById(Long userId) {
+ SysUser sysUser = baseMapper.selectOne(new LambdaQueryWrapper<SysUser>()
+ .select(SysUser::getEmail).eq(SysUser::getUserId, userId));
+ return ObjectUtil.isNull(sysUser) ? null : sysUser.getEmail();
+ }
+
+ @Override
+ public List<UserDTO> selectListByIds(List<Long> userIds) {
+ if (CollUtil.isEmpty(userIds)) {
+ return List.of();
+ }
+ List<SysUserVo> list = this.selectUserByIds(userIds, null);
+ return BeanUtil.copyToList(list, UserDTO.class);
+ }
+
+ @Override
+ public List<Long> selectUserIdsByRoleIds(List<Long> roleIds) {
+ List<SysUserRole> userRoles = userRoleMapper.selectList(
+ new LambdaQueryWrapper<SysUserRole>().in(SysUserRole::getRoleId, roleIds));
+ return StreamUtils.toList(userRoles, SysUserRole::getUserId);
+ }
+
}
diff --git a/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysDeptMapper.xml b/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysDeptMapper.xml
index bba949d..6ad866f 100644
--- a/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysDeptMapper.xml
+++ b/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysDeptMapper.xml
@@ -8,11 +8,18 @@
</resultMap>
<select id="selectDeptList" resultMap="SysDeptResult">
- select * from sys_dept ${ew.getCustomSqlSegment}
+ select
+ <if test="ew.getSqlSelect != null">
+ ${ew.getSqlSelect}
+ </if>
+ <if test="ew.getSqlSelect == null">
+ *
+ </if>
+ from sys_dept ${ew.getCustomSqlSegment}
</select>
- <select id="selectDeptById" resultMap="SysDeptResult">
- select * from sys_dept where del_flag = '0' and dept_id = #{deptId}
+ <select id="countDeptById" resultType="Long">
+ select count(*) from sys_dept where del_flag = '0' and dept_id = #{deptId}
</select>
<select id="selectDeptListByRoleId" resultType="Long">
diff --git a/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysPostMapper.xml b/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysPostMapper.xml
index d2108eb..322403f 100644
--- a/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysPostMapper.xml
+++ b/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysPostMapper.xml
@@ -7,20 +7,23 @@
<resultMap type="org.dromara.system.domain.vo.SysPostVo" id="SysPostResult">
</resultMap>
- <select id="selectPostListByUserId" parameterType="Long" resultType="Long">
- select p.post_id
+ <select id="selectPagePostList" resultMap="SysPostResult">
+ select
+ <if test="ew.getSqlSelect != null">
+ ${ew.getSqlSelect}
+ </if>
+ <if test="ew.getSqlSelect == null">
+ *
+ </if>
+ from sys_post ${ew.getCustomSqlSegment}
+ </select>
+
+ <select id="selectPostsByUserId" parameterType="Long" resultMap="SysPostResult">
+ select p.post_id, p.dept_id, p.post_name, p.post_code, p.post_category
from sys_post p
left join sys_user_post up on up.post_id = p.post_id
left join sys_user u on u.user_id = up.user_id
where u.user_id = #{userId}
- </select>
-
- <select id="selectPostsByUserName" parameterType="String" resultMap="SysPostResult">
- select p.post_id, p.post_name, p.post_code
- from sys_post p
- left join sys_user_post up on up.post_id = p.post_id
- left join sys_user u on u.user_id = up.user_id
- where u.user_name = #{userName}
</select>
</mapper>
diff --git a/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysRoleMapper.xml b/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysRoleMapper.xml
index b191698..7b8bba7 100644
--- a/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysRoleMapper.xml
+++ b/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysRoleMapper.xml
@@ -40,23 +40,17 @@
WHERE r.del_flag = '0' and sur.user_id = #{userId}
</select>
- <select id="selectRoleListByUserId" parameterType="Long" resultType="Long">
- select r.role_id
- from sys_role r
- left join sys_user_role sur on sur.role_id = r.role_id
- left join sys_user u on u.user_id = sur.user_id
- where u.user_id = #{userId}
- </select>
-
- <select id="selectRolesByUserName" parameterType="String" resultMap="SysRoleResult">
+ <select id="selectRolesByUserId" parameterType="Long" resultMap="SysRoleResult">
select r.role_id,
r.role_name,
r.role_key,
- r.role_sort
+ r.role_sort,
+ r.data_scope,
+ r.status
from sys_role r
left join sys_user_role sur on sur.role_id = r.role_id
left join sys_user u on u.user_id = sur.user_id
- WHERE r.del_flag = '0' and u.user_name = #{userName}
+ WHERE r.del_flag = '0' and sur.user_id = #{userId}
</select>
<select id="selectRoleById" resultMap="SysRoleResult">
diff --git a/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysUserMapper.xml b/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysUserMapper.xml
index 7af7dd0..ded6fa8 100644
--- a/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysUserMapper.xml
+++ b/ruoyi-modules/ruoyi-system/src/main/resources/mapper/system/SysUserMapper.xml
@@ -4,78 +4,40 @@
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="org.dromara.system.mapper.SysUserMapper">
- <!-- 澶氱粨鏋勫祵濂楄嚜鍔ㄦ槧灏勯渶甯︿笂姣忎釜瀹炰綋鐨勪富閿甶d 鍚﹀垯鏄犲皠浼氬け璐� -->
<resultMap type="org.dromara.system.domain.vo.SysUserVo" id="SysUserResult">
<id property="userId" column="user_id"/>
- <result property="deptId" column="dept_id"/>
- <association property="dept" column="dept_id" resultMap="deptResult"/>
- <collection property="roles" javaType="java.util.List" resultMap="RoleResult"/>
</resultMap>
-
- <resultMap id="deptResult" type="org.dromara.system.domain.vo.SysDeptVo">
- <id property="deptId" column="dept_id"/>
- <result property="email" column="dept_email"/>
- <result property="status" column="dept_status"/>
- <result property="createTime" column="dept_create_time"/>
+ <resultMap type="org.dromara.system.domain.vo.SysUserExportVo" id="SysUserExportResult">
+ <id property="userId" column="user_id"/>
</resultMap>
-
- <resultMap id="RoleResult" type="org.dromara.system.domain.vo.SysRoleVo">
- <id property="roleId" column="role_id"/>
- <result property="status" column="role_status"/>
- <result property="createTime" column="role_create_time"/>
- </resultMap>
-
- <sql id="selectUserVo">
- select u.user_id,
- u.tenant_id,
- u.dept_id,
- u.user_name,
- u.nick_name,
- u.user_type,
- u.email,
- u.avatar,
- u.phonenumber,
- u.password,
- u.sex,
- u.status,
- u.del_flag,
- u.login_ip,
- u.login_date,
- u.create_by,
- u.create_time,
- u.remark,
- d.dept_id,
- d.parent_id,
- d.ancestors,
- d.dept_name,
- d.order_num,
- d.leader,
- d.status as dept_status,
- d.email as dept_email,
- d.create_time as dept_cteate_time,
- r.role_id,
- r.role_name,
- r.role_key,
- r.role_sort,
- r.data_scope,
- r.status as role_status
- from sys_user u
- left join sys_dept d on u.dept_id = d.dept_id
- left join sys_user_role sur on u.user_id = sur.user_id
- left join sys_role r on r.role_id = sur.role_id
- </sql>
<select id="selectPageUserList" resultMap="SysUserResult">
- select u.user_id, u.dept_id, u.nick_name, u.user_name, u.email, u.avatar, u.phonenumber, u.sex,
- u.status, u.del_flag, u.login_ip, u.login_date, u.create_by, u.create_time, u.remark,
- d.dept_name, d.leader, u1.user_name as leaderName
+ select
+ <if test="ew.getSqlSelect != null">
+ ${ew.getSqlSelect}
+ </if>
+ <if test="ew.getSqlSelect == null">
+ u.user_id, u.dept_id, u.nick_name, u.user_name, u.email, u.avatar, u.phonenumber, u.sex,
+ u.status, u.del_flag, u.login_ip, u.login_date, u.create_by, u.create_time, u.remark
+ </if>
from sys_user u
- left join sys_dept d on u.dept_id = d.dept_id
- left join sys_user u1 on u1.user_id = d.leader
${ew.getCustomSqlSegment}
</select>
<select id="selectUserList" resultMap="SysUserResult">
+ select
+ <if test="ew.getSqlSelect != null">
+ ${ew.getSqlSelect}
+ </if>
+ <if test="ew.getSqlSelect == null">
+ u.user_id, u.dept_id, u.nick_name, u.user_name, u.email, u.avatar, u.phonenumber, u.sex,
+ u.status, u.del_flag, u.login_ip, u.login_date, u.create_by, u.create_time, u.remark
+ </if>
+ from sys_user u
+ ${ew.getCustomSqlSegment}
+ </select>
+
+ <select id="selectUserExportList" resultMap="SysUserExportResult">
select u.user_id, u.dept_id, u.nick_name, u.user_name, u.email, u.avatar, u.phonenumber, u.sex,
u.status, u.del_flag, u.login_ip, u.login_date, u.create_by, u.create_time, u.remark,
d.dept_name, d.leader, u1.user_name as leaderName
@@ -103,24 +65,8 @@
${ew.getCustomSqlSegment}
</select>
- <select id="selectUserByUserName" parameterType="String" resultMap="SysUserResult">
- <include refid="selectUserVo"/>
- where u.del_flag = '0' and u.user_name = #{userName}
- </select>
-
- <select id="selectUserByPhonenumber" parameterType="String" resultMap="SysUserResult">
- <include refid="selectUserVo"/>
- where u.del_flag = '0' and u.phonenumber = #{phonenumber}
- </select>
-
- <select id="selectUserByEmail" parameterType="String" resultMap="SysUserResult">
- <include refid="selectUserVo"/>
- where u.del_flag = '0' and u.email = #{email}
- </select>
-
- <select id="selectUserById" parameterType="Long" resultMap="SysUserResult">
- <include refid="selectUserVo"/>
- where u.del_flag = '0' and u.user_id = #{userId}
+ <select id="countUserById" resultType="Long">
+ select count(*) from sys_user where del_flag = '0' and user_id = #{userId}
</select>
diff --git a/ruoyi-modules/ruoyi-workflow/pom.xml b/ruoyi-modules/ruoyi-workflow/pom.xml
new file mode 100644
index 0000000..0217098
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/pom.xml
@@ -0,0 +1,116 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ <parent>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-modules</artifactId>
+ <version>${revision}</version>
+ <relativePath>../pom.xml</relativePath>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <packaging>jar</packaging>
+ <artifactId>ruoyi-workflow</artifactId>
+
+ <description>
+ 宸ヤ綔娴佹ā鍧�
+ </description>
+
+ <dependencies>
+
+ <!--寮曞叆flowable渚濊禆-->
+ <dependency>
+ <groupId>org.flowable</groupId>
+ <artifactId>flowable-spring-boot-autoconfigure</artifactId>
+ <exclusions>
+ <exclusion>
+ <groupId>org.flowable</groupId>
+ <artifactId>flowable-spring-security</artifactId>
+ </exclusion>
+ </exclusions>
+ </dependency>
+
+ <dependency>
+ <groupId>org.flowable</groupId>
+ <artifactId>flowable-spring-configurator</artifactId>
+ </dependency>
+
+ <dependency>
+ <groupId>org.flowable</groupId>
+ <artifactId>flowable-spring-boot-starter-actuator</artifactId>
+ </dependency>
+
+ <!-- 缁樺埗flowable娴佺▼鍥� -->
+ <dependency>
+ <groupId>org.flowable</groupId>
+ <artifactId>flowable-image-generator</artifactId>
+ </dependency>
+
+ <!-- flowable json 杞崲 -->
+ <dependency>
+ <groupId>org.flowable</groupId>
+ <artifactId>flowable-json-converter</artifactId>
+ <version>6.8.0</version>
+ </dependency>
+
+ <!-- svg杞琾ng鍥剧墖宸ュ叿-->
+ <dependency>
+ <groupId>org.apache.xmlgraphics</groupId>
+ <artifactId>batik-all</artifactId>
+ <version>1.10</version>
+ <exclusions>
+ <exclusion>
+ <groupId>xalan</groupId>
+ <artifactId>xalan</artifactId>
+ </exclusion>
+ </exclusions>
+ </dependency>
+
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-websocket</artifactId>
+ </dependency>
+
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-mail</artifactId>
+ </dependency>
+
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-sms</artifactId>
+ </dependency>
+
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-mybatis</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-web</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-log</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-idempotent</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-excel</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-translation</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.dromara</groupId>
+ <artifactId>ruoyi-common-tenant</artifactId>
+ </dependency>
+
+ </dependencies>
+
+</project>
+
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/annotation/FlowListenerAnnotation.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/annotation/FlowListenerAnnotation.java
new file mode 100644
index 0000000..5ea262d
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/annotation/FlowListenerAnnotation.java
@@ -0,0 +1,27 @@
+package org.dromara.workflow.annotation;
+
+
+import java.lang.annotation.*;
+
+/**
+ * 娴佺▼浠诲姟鐩戝惉娉ㄨВ
+ *
+ * @author may
+ * @date 2023-12-27
+ */
+@Target({ElementType.TYPE})
+@Retention(RetentionPolicy.RUNTIME)
+@Documented
+@Inherited
+public @interface FlowListenerAnnotation {
+
+ /**
+ * 娴佺▼瀹氫箟key
+ */
+ String processDefinitionKey();
+
+ /**
+ * 鑺傜偣id
+ */
+ String taskDefId() default "";
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/constant/FlowConstant.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/constant/FlowConstant.java
new file mode 100644
index 0000000..df27d3c
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/constant/FlowConstant.java
@@ -0,0 +1,137 @@
+package org.dromara.workflow.common.constant;
+
+
+/**
+ * 宸ヤ綔娴佸父閲�
+ *
+ * @author may
+ */
+public interface FlowConstant {
+
+ String MESSAGE_CURRENT_TASK_IS_NULL = "褰撳墠浠诲姟涓嶅瓨鍦ㄦ垨浣犱笉鏄换鍔″姙鐞嗕汉锛�";
+
+ String MESSAGE_SUSPENDED = "褰撳墠浠诲姟宸叉寕璧蜂笉鍙鎵癸紒";
+
+ /**
+ * 杩炵嚎
+ */
+ String SEQUENCE_FLOW = "sequenceFlow";
+
+ /**
+ * 骞惰缃戝叧
+ */
+ String PARALLEL_GATEWAY = "parallelGateway";
+
+ /**
+ * 鎺掑畠缃戝叧
+ */
+ String EXCLUSIVE_GATEWAY = "exclusiveGateway";
+
+ /**
+ * 鍖呭惈缃戝叧
+ */
+ String INCLUSIVE_GATEWAY = "inclusiveGateway";
+
+ /**
+ * 缁撴潫鑺傜偣
+ */
+ String END_EVENT = "endEvent";
+
+
+ /**
+ * 娴佺▼濮旀淳鏍囪瘑
+ */
+ String PENDING = "PENDING";
+
+ /**
+ * 鍊欓�変汉鏍囪瘑
+ */
+ String CANDIDATE = "candidate";
+
+ /**
+ * 浼氱浠诲姟鎬绘暟
+ */
+ String NUMBER_OF_INSTANCES = "nrOfInstances";
+
+ /**
+ * 姝e湪鎵ц鐨勪細绛炬�绘暟
+ */
+ String NUMBER_OF_ACTIVE_INSTANCES = "nrOfActiveInstances";
+
+ /**
+ * 宸插畬鎴愮殑浼氱浠诲姟鎬绘暟
+ */
+ String NUMBER_OF_COMPLETED_INSTANCES = "nrOfCompletedInstances";
+
+ /**
+ * 寰幆鐨勭储寮曞�硷紝鍙互浣跨敤elementIndexVariable灞炴�т慨鏀筶oopCounter鐨勫彉閲忓悕
+ */
+ String LOOP_COUNTER = "loopCounter";
+
+ String ZIP = "ZIP";
+
+ /**
+ * 娴佺▼瀹炰緥瀵硅薄
+ */
+ String PROCESS_INSTANCE_VO = "processInstanceVo";
+
+ /**
+ * 娴佺▼瀹氫箟閰嶇疆
+ */
+ String WF_DEFINITION_CONFIG_VO = "wfDefinitionConfigVo";
+
+ /**
+ * 鑺傜偣閰嶇疆
+ */
+ String WF_NODE_CONFIG_VO = "wfNodeConfigVo";
+
+ /**
+ * 娴佺▼鍙戣捣浜�
+ */
+ String INITIATOR = "initiator";
+
+ /**
+ * 娴佺▼瀹炰緥id
+ */
+ String PROCESS_INSTANCE_ID = "processInstanceId";
+
+ /**
+ * 涓氬姟id
+ */
+ String BUSINESS_KEY = "businessKey";
+
+ /**
+ * 娴佺▼瀹氫箟id
+ */
+ String PROCESS_DEFINITION_ID = "processDefinitionId";
+
+ /**
+ * 寮�鍚烦杩囪〃杈惧紡鍙橀噺
+ */
+ String FLOWABLE_SKIP_EXPRESSION_ENABLED = "_FLOWABLE_SKIP_EXPRESSION_ENABLED";
+
+ /**
+ * 妯″瀷鏍囪瘑key鍛藉悕瑙勮寖姝e垯琛ㄨ揪寮�
+ */
+ String MODEL_KEY_PATTERN = "^[a-zA-Z][a-zA-Z0-9_]{0,254}$";
+
+ /**
+ * 鐢ㄦ埛浠诲姟
+ */
+ String USER_TASK = "userTask";
+
+ /**
+ * 浼氱
+ */
+ String MULTI_INSTANCE = "multiInstance";
+
+ /**
+ * 鏄�
+ */
+ String TRUE = "0";
+
+ /**
+ * 鍚�
+ */
+ String FALSE = "1";
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/BusinessStatusEnum.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/BusinessStatusEnum.java
new file mode 100644
index 0000000..6eb6ffe
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/BusinessStatusEnum.java
@@ -0,0 +1,152 @@
+package org.dromara.workflow.common.enums;
+
+import cn.hutool.core.util.StrUtil;
+import lombok.AllArgsConstructor;
+import lombok.Getter;
+import org.dromara.common.core.exception.ServiceException;
+import org.dromara.common.core.utils.StringUtils;
+
+import java.util.Arrays;
+
+/**
+ * 涓氬姟鐘舵�佹灇涓�
+ *
+ * @author may
+ */
+@Getter
+@AllArgsConstructor
+public enum BusinessStatusEnum {
+ /**
+ * 宸叉挙閿�
+ */
+ CANCEL("cancel", "宸叉挙閿�"),
+ /**
+ * 鑽夌
+ */
+ DRAFT("draft", "鑽夌"),
+ /**
+ * 寰呭鏍�
+ */
+ WAITING("waiting", "寰呭鏍�"),
+ /**
+ * 宸插畬鎴�
+ */
+ FINISH("finish", "宸插畬鎴�"),
+ /**
+ * 宸蹭綔搴�
+ */
+ INVALID("invalid", "宸蹭綔搴�"),
+ /**
+ * 宸查��鍥�
+ */
+ BACK("back", "宸查��鍥�"),
+ /**
+ * 宸茬粓姝�
+ */
+ TERMINATION("termination", "宸茬粓姝�");
+
+ /**
+ * 鐘舵��
+ */
+ private final String status;
+
+ /**
+ * 鎻忚堪
+ */
+ private final String desc;
+
+ /**
+ * 鑾峰彇涓氬姟鐘舵��
+ *
+ * @param status 鐘舵��
+ */
+ public static String findByStatus(String status) {
+ if (StringUtils.isBlank(status)) {
+ return StrUtil.EMPTY;
+ }
+ return Arrays.stream(BusinessStatusEnum.values())
+ .filter(statusEnum -> statusEnum.getStatus().equals(status))
+ .findFirst()
+ .map(BusinessStatusEnum::getDesc)
+ .orElse(StrUtil.EMPTY);
+ }
+
+ /**
+ * 鍚姩娴佺▼鏍¢獙
+ *
+ * @param status 鐘舵��
+ */
+ public static void checkStartStatus(String status) {
+ if (WAITING.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡鎻愪氦杩囩敵璇�,姝e湪瀹℃壒涓紒");
+ } else if (FINISH.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡瀹屾垚鐢宠锛�");
+ } else if (INVALID.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡浣滃簾锛�");
+ } else if (TERMINATION.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡缁堟锛�");
+ } else if (StringUtils.isBlank(status)) {
+ throw new ServiceException("娴佺▼鐘舵�佷负绌猴紒");
+ }
+ }
+
+ /**
+ * 鎾ら攢娴佺▼鏍¢獙
+ *
+ * @param status 鐘舵��
+ */
+ public static void checkCancelStatus(String status) {
+ if (CANCEL.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡鎾ら攢锛�");
+ } else if (FINISH.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡瀹屾垚鐢宠锛�");
+ } else if (INVALID.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡浣滃簾锛�");
+ } else if (TERMINATION.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡缁堟锛�");
+ } else if (BACK.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡閫�鍥烇紒");
+ } else if (StringUtils.isBlank(status)) {
+ throw new ServiceException("娴佺▼鐘舵�佷负绌猴紒");
+ }
+ }
+
+ /**
+ * 椹冲洖娴佺▼鏍¢獙
+ *
+ * @param status 鐘舵��
+ */
+ public static void checkBackStatus(String status) {
+ if (BACK.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡閫�鍥烇紒");
+ } else if (FINISH.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡瀹屾垚鐢宠锛�");
+ } else if (INVALID.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡浣滃簾锛�");
+ } else if (TERMINATION.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡缁堟锛�");
+ } else if (CANCEL.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡鎾ら攢锛�");
+ } else if (StringUtils.isBlank(status)) {
+ throw new ServiceException("娴佺▼鐘舵�佷负绌猴紒");
+ }
+ }
+
+ /**
+ * 浣滃簾,缁堟娴佺▼鏍¢獙
+ *
+ * @param status 鐘舵��
+ */
+ public static void checkInvalidStatus(String status) {
+ if (FINISH.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡瀹屾垚鐢宠锛�");
+ } else if (INVALID.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡浣滃簾锛�");
+ } else if (TERMINATION.getStatus().equals(status)) {
+ throw new ServiceException("璇ュ崟鎹凡缁堟锛�");
+ } else if (StringUtils.isBlank(status)) {
+ throw new ServiceException("娴佺▼鐘舵�佷负绌猴紒");
+ }
+ }
+}
+
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/FormTypeEnum.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/FormTypeEnum.java
new file mode 100644
index 0000000..083ab7b
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/FormTypeEnum.java
@@ -0,0 +1,54 @@
+package org.dromara.workflow.common.enums;
+
+import cn.hutool.core.util.StrUtil;
+import lombok.AllArgsConstructor;
+import lombok.Getter;
+import org.apache.commons.lang3.StringUtils;
+
+import java.util.Arrays;
+
+/**
+ * 浠诲姟鐘舵�佹灇涓�
+ *
+ * @author may
+ */
+@Getter
+@AllArgsConstructor
+public enum FormTypeEnum {
+ /**
+ * 鑷畾涔夎〃鍗�
+ */
+ STATIC("static", "鑷畾涔夎〃鍗�"),
+ /**
+ * 鍔ㄦ�佽〃鍗�
+ */
+ DYNAMIC("dynamic", "鍔ㄦ�佽〃鍗�");
+
+ /**
+ * 绫诲瀷
+ */
+ private final String type;
+
+ /**
+ * 鎻忚堪
+ */
+ private final String desc;
+
+ /**
+ * 琛ㄥ崟绫诲瀷
+ *
+ * @param formType 琛ㄥ崟绫诲瀷
+ */
+ public static String findByType(String formType) {
+ if (StringUtils.isBlank(formType)) {
+ return StrUtil.EMPTY;
+ }
+
+ return Arrays.stream(FormTypeEnum.values())
+ .filter(statusEnum -> statusEnum.getType().equals(formType))
+ .findFirst()
+ .map(FormTypeEnum::getDesc)
+ .orElse(StrUtil.EMPTY);
+ }
+}
+
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/MessageTypeEnum.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/MessageTypeEnum.java
new file mode 100644
index 0000000..a282958
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/MessageTypeEnum.java
@@ -0,0 +1,51 @@
+package org.dromara.workflow.common.enums;
+
+import lombok.AllArgsConstructor;
+import lombok.Getter;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+/**
+ * 娑堟伅绫诲瀷鏋氫妇
+ *
+ * @author may
+ */
+@Getter
+@AllArgsConstructor
+public enum MessageTypeEnum {
+ /**
+ * 绔欏唴淇�
+ */
+ SYSTEM_MESSAGE("1", "绔欏唴淇�"),
+ /**
+ * 閭
+ */
+ EMAIL_MESSAGE("2", "閭"),
+ /**
+ * 鐭俊
+ */
+ SMS_MESSAGE("3", "鐭俊");
+
+ private final String code;
+
+ private final String desc;
+
+ private final static Map<String, MessageTypeEnum> MESSAGE_TYPE_ENUM_MAP = new ConcurrentHashMap<>(MessageTypeEnum.values().length);
+
+ static {
+ for (MessageTypeEnum messageType : MessageTypeEnum.values()) {
+ MESSAGE_TYPE_ENUM_MAP.put(messageType.code, messageType);
+ }
+ }
+
+ /**
+ * 鏍规嵁娑堟伅绫诲瀷 code 鑾峰彇 MessageTypeEnum
+ * @param code 娑堟伅绫诲瀷code
+ * @return MessageTypeEnum
+ */
+ public static MessageTypeEnum getByCode(String code) {
+ return MESSAGE_TYPE_ENUM_MAP.get(code);
+ }
+}
+
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/TaskStatusEnum.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/TaskStatusEnum.java
new file mode 100644
index 0000000..7b2f55c
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/common/enums/TaskStatusEnum.java
@@ -0,0 +1,94 @@
+package org.dromara.workflow.common.enums;
+
+import cn.hutool.core.util.StrUtil;
+import lombok.AllArgsConstructor;
+import lombok.Getter;
+import org.apache.commons.lang3.StringUtils;
+
+import java.util.Arrays;
+
+/**
+ * 浠诲姟鐘舵�佹灇涓�
+ *
+ * @author may
+ */
+@Getter
+@AllArgsConstructor
+public enum TaskStatusEnum {
+ /**
+ * 鎾ら攢
+ */
+ CANCEL("cancel", "鎾ら攢"),
+ /**
+ * 閫氳繃
+ */
+ PASS("pass", "閫氳繃"),
+ /**
+ * 寰呭鏍�
+ */
+ WAITING("waiting", "寰呭鏍�"),
+ /**
+ * 浣滃簾
+ */
+ INVALID("invalid", "浣滃簾"),
+ /**
+ * 閫�鍥�
+ */
+ BACK("back", "閫�鍥�"),
+ /**
+ * 缁堟
+ */
+ TERMINATION("termination", "缁堟"),
+ /**
+ * 杞姙
+ */
+ TRANSFER("transfer", "杞姙"),
+ /**
+ * 濮旀墭
+ */
+ PENDING("pending", "濮旀墭"),
+ /**
+ * 鎶勯��
+ */
+ COPY("copy", "鎶勯��"),
+ /**
+ * 鍔犵
+ */
+ SIGN("sign", "鍔犵"),
+ /**
+ * 鍑忕
+ */
+ SIGN_OFF("sign_off", "鍑忕"),
+ /**
+ * 瓒呮椂
+ */
+ TIMEOUT("timeout", "瓒呮椂");
+
+ /**
+ * 鐘舵��
+ */
+ private final String status;
+
+ /**
+ * 鎻忚堪
+ */
+ private final String desc;
+
+ /**
+ * 浠诲姟涓氬姟鐘舵��
+ *
+ * @param status 鐘舵��
+ */
+ public static String findByStatus(String status) {
+ if (StringUtils.isBlank(status)) {
+ return StrUtil.EMPTY;
+ }
+
+ return Arrays.stream(TaskStatusEnum.values())
+ .filter(statusEnum -> statusEnum.getStatus().equals(status))
+ .findFirst()
+ .map(TaskStatusEnum::getDesc)
+ .orElse(StrUtil.EMPTY);
+ }
+}
+
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActModelController.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActModelController.java
new file mode 100644
index 0000000..3332f86
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActModelController.java
@@ -0,0 +1,147 @@
+package org.dromara.workflow.controller;
+
+import jakarta.servlet.http.HttpServletResponse;
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.NotEmpty;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.domain.R;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import org.dromara.common.idempotent.annotation.RepeatSubmit;
+import org.dromara.common.log.annotation.Log;
+import org.dromara.common.log.enums.BusinessType;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.web.core.BaseController;
+import org.dromara.workflow.domain.bo.ModelBo;
+import org.dromara.workflow.domain.vo.ModelVo;
+import org.dromara.workflow.service.IActModelService;
+import org.flowable.engine.RepositoryService;
+import org.flowable.engine.repository.Model;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * 妯″瀷绠$悊 鎺у埗灞�
+ *
+ * @author may
+ */
+@Validated
+@RequiredArgsConstructor
+@RestController
+@RequestMapping("/workflow/model")
+public class ActModelController extends BaseController {
+
+ private final RepositoryService repositoryService;
+
+ private final IActModelService actModelService;
+
+
+ /**
+ * 鍒嗛〉鏌ヨ妯″瀷
+ *
+ * @param modelBo 妯″瀷鍙傛暟
+ */
+ @GetMapping("/list")
+ public TableDataInfo<Model> page(ModelBo modelBo, PageQuery pageQuery) {
+ return actModelService.page(modelBo, pageQuery);
+ }
+
+ /**
+ * 鏂板妯″瀷
+ *
+ * @param modelBo 妯″瀷璇锋眰瀵硅薄
+ */
+ @Log(title = "妯″瀷绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/save")
+ public R<Void> saveNewModel(@Validated(AddGroup.class) @RequestBody ModelBo modelBo) {
+ return toAjax(actModelService.saveNewModel(modelBo));
+ }
+
+ /**
+ * 鏌ヨ妯″瀷
+ *
+ * @param id 妯″瀷id
+ */
+ @GetMapping("/getInfo/{id}")
+ public R<ModelVo> getInfo(@NotBlank(message = "妯″瀷id涓嶈兘涓虹┖") @PathVariable String id) {
+ return R.ok(actModelService.getInfo(id));
+ }
+
+ /**
+ * 淇敼妯″瀷淇℃伅
+ *
+ * @param modelBo 妯″瀷鏁版嵁
+ */
+ @Log(title = "妯″瀷绠$悊", businessType = BusinessType.UPDATE)
+ @RepeatSubmit()
+ @PutMapping(value = "/update")
+ public R<Void> update(@RequestBody ModelBo modelBo) {
+ return toAjax(actModelService.update(modelBo));
+ }
+
+ /**
+ * 缂栬緫XMl妯″瀷
+ *
+ * @param modelBo 妯″瀷鏁版嵁
+ */
+ @Log(title = "妯″瀷绠$悊", businessType = BusinessType.UPDATE)
+ @RepeatSubmit()
+ @PutMapping(value = "/editModelXml")
+ public R<Void> editModel(@Validated(EditGroup.class) @RequestBody ModelBo modelBo) {
+ return toAjax(actModelService.editModelXml(modelBo));
+ }
+
+ /**
+ * 鍒犻櫎娴佺▼妯″瀷
+ *
+ * @param ids 妯″瀷id
+ */
+ @Log(title = "妯″瀷绠$悊", businessType = BusinessType.DELETE)
+ @RepeatSubmit()
+ @DeleteMapping("/{ids}")
+ @Transactional(rollbackFor = Exception.class)
+ public R<Void> delete(@NotEmpty(message = "涓婚敭涓嶈兘涓虹┖") @PathVariable String[] ids) {
+ Arrays.stream(ids).parallel().forEachOrdered(repositoryService::deleteModel);
+ return R.ok();
+ }
+
+ /**
+ * 妯″瀷閮ㄧ讲
+ *
+ * @param id 妯″瀷id
+ */
+ @Log(title = "妯″瀷绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/modelDeploy/{id}")
+ public R<Void> deploy(@NotBlank(message = "妯″瀷id涓嶈兘涓虹┖") @PathVariable("id") String id) {
+ return toAjax(actModelService.modelDeploy(id));
+ }
+
+ /**
+ * 瀵煎嚭妯″瀷zip鍘嬬缉鍖�
+ *
+ * @param modelIds 妯″瀷id
+ * @param response 鐩稿簲
+ */
+ @GetMapping("/export/zip/{modelIds}")
+ public void exportZip(@NotEmpty(message = "妯″瀷id涓嶈兘涓虹┖") @PathVariable List<String> modelIds,
+ HttpServletResponse response) {
+ actModelService.exportZip(modelIds, response);
+ }
+
+ /**
+ * 澶嶅埗妯″瀷
+ *
+ * @param modelBo 妯″瀷鏁版嵁
+ */
+ @PostMapping("/copyModel")
+ public R<Void> copyModel(@RequestBody ModelBo modelBo) {
+ return toAjax(actModelService.copyModel(modelBo));
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActProcessDefinitionController.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActProcessDefinitionController.java
new file mode 100644
index 0000000..5198bd1
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActProcessDefinitionController.java
@@ -0,0 +1,147 @@
+package org.dromara.workflow.controller;
+
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.NotEmpty;
+import jakarta.validation.constraints.NotNull;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.domain.R;
+import org.dromara.common.idempotent.annotation.RepeatSubmit;
+import org.dromara.common.log.annotation.Log;
+import org.dromara.common.log.enums.BusinessType;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.web.core.BaseController;
+import org.dromara.workflow.domain.bo.ProcessDefinitionBo;
+import org.dromara.workflow.domain.vo.ProcessDefinitionVo;
+import org.dromara.workflow.service.IActProcessDefinitionService;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+import org.springframework.web.multipart.MultipartFile;
+
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+
+/**
+ * 娴佺▼瀹氫箟绠$悊 鎺у埗灞�
+ *
+ * @author may
+ */
+@Validated
+@RequiredArgsConstructor
+@RestController
+@RequestMapping("/workflow/processDefinition")
+public class ActProcessDefinitionController extends BaseController {
+
+ private final IActProcessDefinitionService actProcessDefinitionService;
+
+ /**
+ * 鍒嗛〉鏌ヨ
+ *
+ * @param bo 鍙傛暟
+ */
+ @GetMapping("/list")
+ public TableDataInfo<ProcessDefinitionVo> page(ProcessDefinitionBo bo, PageQuery pageQuery) {
+ return actProcessDefinitionService.page(bo, pageQuery);
+ }
+
+ /**
+ * 鏌ヨ鍘嗗彶娴佺▼瀹氫箟鍒楄〃
+ *
+ * @param key 娴佺▼瀹氫箟key
+ */
+ @GetMapping("/getListByKey/{key}")
+ public R<List<ProcessDefinitionVo>> getListByKey(@NotEmpty(message = "娴佺▼瀹氫箟key涓嶈兘涓虹┖") @PathVariable String key) {
+ return R.ok("鎿嶄綔鎴愬姛", actProcessDefinitionService.getListByKey(key));
+ }
+
+ /**
+ * 鏌ョ湅娴佺▼瀹氫箟鍥剧墖
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ @GetMapping("/definitionImage/{processDefinitionId}")
+ public R<String> definitionImage(@PathVariable String processDefinitionId) {
+ return R.ok("鎿嶄綔鎴愬姛", actProcessDefinitionService.definitionImage(processDefinitionId));
+ }
+
+ /**
+ * 鏌ョ湅娴佺▼瀹氫箟xml鏂囦欢
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ @GetMapping("/definitionXml/{processDefinitionId}")
+ public R<Map<String, Object>> definitionXml(@NotBlank(message = "娴佺▼瀹氫箟id涓嶈兘涓虹┖") @PathVariable String processDefinitionId) {
+ Map<String, Object> map = new HashMap<>();
+ String xmlStr = actProcessDefinitionService.definitionXml(processDefinitionId);
+ map.put("xml", Arrays.asList(xmlStr.split("\n")));
+ map.put("xmlStr", xmlStr);
+ return R.ok(map);
+ }
+
+ /**
+ * 鍒犻櫎娴佺▼瀹氫箟
+ *
+ * @param deploymentIds 閮ㄧ讲id
+ * @param processDefinitionIds 娴佺▼瀹氫箟id
+ */
+ @Log(title = "娴佺▼瀹氫箟绠$悊", businessType = BusinessType.DELETE)
+ @DeleteMapping("/{deploymentIds}/{processDefinitionIds}")
+ public R<Void> deleteDeployment(@NotNull(message = "娴佺▼閮ㄧ讲id涓嶈兘涓虹┖") @PathVariable List<String> deploymentIds,
+ @NotNull(message = "娴佺▼瀹氫箟id涓嶈兘涓虹┖") @PathVariable List<String> processDefinitionIds) {
+ return toAjax(actProcessDefinitionService.deleteDeployment(deploymentIds, processDefinitionIds));
+ }
+
+ /**
+ * 婵�娲绘垨鑰呮寕璧锋祦绋嬪畾涔�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ @Log(title = "娴佺▼瀹氫箟绠$悊", businessType = BusinessType.UPDATE)
+ @RepeatSubmit()
+ @PutMapping("/updateDefinitionState/{processDefinitionId}")
+ public R<Void> updateDefinitionState(@NotBlank(message = "娴佺▼瀹氫箟id涓嶈兘涓虹┖") @PathVariable String processDefinitionId) {
+ return toAjax(actProcessDefinitionService.updateDefinitionState(processDefinitionId));
+ }
+
+ /**
+ * 杩佺Щ娴佺▼瀹氫箟
+ *
+ * @param currentProcessDefinitionId 褰撳墠娴佺▼瀹氫箟id
+ * @param fromProcessDefinitionId 闇�瑕佽縼绉诲埌鐨勬祦绋嬪畾涔塱d
+ */
+ @Log(title = "娴佺▼瀹氫箟绠$悊", businessType = BusinessType.UPDATE)
+ @RepeatSubmit()
+ @PutMapping("/migrationDefinition/{currentProcessDefinitionId}/{fromProcessDefinitionId}")
+ public R<Void> migrationDefinition(@NotBlank(message = "褰撳墠娴佺▼瀹氫箟id") @PathVariable String currentProcessDefinitionId,
+ @NotBlank(message = "闇�瑕佽縼绉诲埌鐨勬祦绋嬪畾涔塱d") @PathVariable String fromProcessDefinitionId) {
+ return toAjax(actProcessDefinitionService.migrationDefinition(currentProcessDefinitionId, fromProcessDefinitionId));
+ }
+
+ /**
+ * 娴佺▼瀹氫箟杞崲涓烘ā鍨�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ @Log(title = "娴佺▼瀹氫箟绠$悊", businessType = BusinessType.UPDATE)
+ @RepeatSubmit()
+ @PutMapping("/convertToModel/{processDefinitionId}")
+ public R<Void> convertToModel(@NotEmpty(message = "娴佺▼瀹氫箟id涓嶈兘涓虹┖") @PathVariable String processDefinitionId) {
+ return toAjax(actProcessDefinitionService.convertToModel(processDefinitionId));
+ }
+
+ /**
+ * 閫氳繃zip鎴杧ml閮ㄧ讲娴佺▼瀹氫箟
+ *
+ * @param file 鏂囦欢
+ * @param categoryCode 鍒嗙被
+ */
+ @Log(title = "娴佺▼瀹氫箟绠$悊", businessType = BusinessType.INSERT)
+ @PostMapping("/deployByFile")
+ public void deployByFile(@RequestParam("file") MultipartFile file, @RequestParam("categoryCode") String categoryCode) {
+ actProcessDefinitionService.deployByFile(file, categoryCode);
+ }
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActProcessInstanceController.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActProcessInstanceController.java
new file mode 100644
index 0000000..142386b
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActProcessInstanceController.java
@@ -0,0 +1,160 @@
+package org.dromara.workflow.controller;
+
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.NotNull;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.domain.R;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.idempotent.annotation.RepeatSubmit;
+import org.dromara.common.log.annotation.Log;
+import org.dromara.common.log.enums.BusinessType;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.web.core.BaseController;
+import org.dromara.workflow.domain.bo.ProcessInstanceBo;
+import org.dromara.workflow.domain.bo.ProcessInvalidBo;
+import org.dromara.workflow.domain.bo.TaskUrgingBo;
+import org.dromara.workflow.domain.vo.ActHistoryInfoVo;
+import org.dromara.workflow.domain.vo.ProcessInstanceVo;
+import org.dromara.workflow.service.IActProcessInstanceService;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.Arrays;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * 娴佺▼瀹炰緥绠$悊 鎺у埗灞�
+ *
+ * @author may
+ */
+@Validated
+@RequiredArgsConstructor
+@RestController
+@RequestMapping("/workflow/processInstance")
+public class ActProcessInstanceController extends BaseController {
+
+ private final IActProcessInstanceService actProcessInstanceService;
+
+ /**
+ * 鍒嗛〉鏌ヨ姝e湪杩愯鐨勬祦绋嬪疄渚�
+ *
+ * @param bo 鍙傛暟
+ */
+ @GetMapping("/getPageByRunning")
+ public TableDataInfo<ProcessInstanceVo> getPageByRunning(ProcessInstanceBo bo, PageQuery pageQuery) {
+ return actProcessInstanceService.getPageByRunning(bo, pageQuery);
+ }
+
+ /**
+ * 鍒嗛〉鏌ヨ宸茬粨鏉熺殑娴佺▼瀹炰緥
+ *
+ * @param bo 鍙傛暟
+ */
+ @GetMapping("/getPageByFinish")
+ public TableDataInfo<ProcessInstanceVo> getPageByFinish(ProcessInstanceBo bo, PageQuery pageQuery) {
+ return actProcessInstanceService.getPageByFinish(bo, pageQuery);
+ }
+
+ /**
+ * 閫氳繃娴佺▼瀹炰緥id鑾峰彇鍘嗗彶娴佺▼鍥�
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ @GetMapping("/getHistoryImage/{processInstanceId}")
+ public R<String> getHistoryImage(@NotBlank(message = "娴佺▼瀹炰緥id涓嶈兘涓虹┖") @PathVariable String processInstanceId) {
+ return R.ok("鎿嶄綔鎴愬姛", actProcessInstanceService.getHistoryImage(processInstanceId));
+ }
+
+ /**
+ * 閫氳繃娴佺▼瀹炰緥id鑾峰彇鍘嗗彶娴佺▼鍥捐繍琛屼腑锛屽巻鍙茬瓑鑺傜偣
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ @GetMapping("/getHistoryList/{processInstanceId}")
+ public R<Map<String, Object>> getHistoryList(@NotBlank(message = "娴佺▼瀹炰緥id涓嶈兘涓虹┖") @PathVariable String processInstanceId) {
+ return R.ok("鎿嶄綔鎴愬姛", actProcessInstanceService.getHistoryList(processInstanceId));
+ }
+
+ /**
+ * 鑾峰彇瀹℃壒璁板綍
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ @GetMapping("/getHistoryRecord/{processInstanceId}")
+ public R<List<ActHistoryInfoVo>> getHistoryRecord(@NotBlank(message = "娴佺▼瀹炰緥id涓嶈兘涓虹┖") @PathVariable String processInstanceId) {
+ return R.ok(actProcessInstanceService.getHistoryRecord(processInstanceId));
+ }
+
+ /**
+ * 浣滃簾娴佺▼瀹炰緥锛屼笉浼氬垹闄ゅ巻鍙茶褰�(鍒犻櫎杩愯涓殑瀹炰緥)
+ *
+ * @param processInvalidBo 鍙傛暟
+ */
+ @Log(title = "娴佺▼瀹炰緥绠$悊", businessType = BusinessType.DELETE)
+ @RepeatSubmit()
+ @PostMapping("/deleteRunInstance")
+ public R<Void> deleteRunInstance(@Validated(AddGroup.class) @RequestBody ProcessInvalidBo processInvalidBo) {
+ return toAjax(actProcessInstanceService.deleteRunInstance(processInvalidBo));
+ }
+
+ /**
+ * 杩愯涓殑瀹炰緥 鍒犻櫎绋嬪疄渚嬶紝鍒犻櫎鍘嗗彶璁板綍锛屽垹闄や笟鍔′笌娴佺▼鍏宠仈淇℃伅
+ *
+ * @param processInstanceIds 娴佺▼瀹炰緥id
+ */
+ @Log(title = "娴佺▼瀹炰緥绠$悊", businessType = BusinessType.DELETE)
+ @RepeatSubmit()
+ @DeleteMapping("/deleteRunAndHisInstance/{processInstanceIds}")
+ public R<Void> deleteRunAndHisInstance(@NotNull(message = "娴佺▼瀹炰緥id涓嶈兘涓虹┖") @PathVariable String[] processInstanceIds) {
+ return toAjax(actProcessInstanceService.deleteRunAndHisInstance(Arrays.asList(processInstanceIds)));
+ }
+
+ /**
+ * 宸插畬鎴愮殑瀹炰緥 鍒犻櫎绋嬪疄渚嬶紝鍒犻櫎鍘嗗彶璁板綍锛屽垹闄や笟鍔′笌娴佺▼鍏宠仈淇℃伅
+ *
+ * @param processInstanceIds 娴佺▼瀹炰緥id
+ */
+ @Log(title = "娴佺▼瀹炰緥绠$悊", businessType = BusinessType.DELETE)
+ @RepeatSubmit()
+ @DeleteMapping("/deleteFinishAndHisInstance/{processInstanceIds}")
+ public R<Void> deleteFinishAndHisInstance(@NotNull(message = "娴佺▼瀹炰緥id涓嶈兘涓虹┖") @PathVariable String[] processInstanceIds) {
+ return toAjax(actProcessInstanceService.deleteFinishAndHisInstance(Arrays.asList(processInstanceIds)));
+ }
+
+ /**
+ * 鎾ら攢娴佺▼鐢宠
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ @Log(title = "娴佺▼瀹炰緥绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/cancelProcessApply/{processInstanceId}")
+ public R<Void> cancelProcessApply(@NotBlank(message = "娴佺▼瀹炰緥id涓嶈兘涓虹┖") @PathVariable String processInstanceId) {
+ return toAjax(actProcessInstanceService.cancelProcessApply(processInstanceId));
+ }
+
+ /**
+ * 鍒嗛〉鏌ヨ褰撳墠鐧诲綍浜哄崟鎹�
+ *
+ * @param bo 鍙傛暟
+ */
+ @GetMapping("/getPageByCurrent")
+ public TableDataInfo<ProcessInstanceVo> getPageByCurrent(ProcessInstanceBo bo, PageQuery pageQuery) {
+ return actProcessInstanceService.getPageByCurrent(bo, pageQuery);
+ }
+
+ /**
+ * 浠诲姟鍌姙(缁欏綋鍓嶄换鍔″姙鐞嗕汉鍙戦�佺珯鍐呬俊锛岄偖浠讹紝鐭俊绛�)
+ *
+ * @param taskUrgingBo 浠诲姟鍌姙
+ */
+ @Log(title = "娴佺▼瀹炰緥绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/taskUrging")
+ public R<Void> taskUrging(@RequestBody TaskUrgingBo taskUrgingBo) {
+ return toAjax(actProcessInstanceService.taskUrging(taskUrgingBo));
+ }
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActTaskController.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActTaskController.java
new file mode 100644
index 0000000..7fc9b95
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/ActTaskController.java
@@ -0,0 +1,295 @@
+package org.dromara.workflow.controller;
+
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.convert.Convert;
+import jakarta.validation.constraints.NotBlank;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.domain.R;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.idempotent.annotation.RepeatSubmit;
+import org.dromara.common.log.annotation.Log;
+import org.dromara.common.log.enums.BusinessType;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.satoken.utils.LoginHelper;
+import org.dromara.common.web.core.BaseController;
+import org.dromara.workflow.domain.WfTaskBackNode;
+import org.dromara.workflow.domain.bo.*;
+import org.dromara.workflow.domain.vo.TaskVo;
+import org.dromara.workflow.domain.vo.VariableVo;
+import org.dromara.workflow.service.IActTaskService;
+import org.dromara.workflow.service.IWfTaskBackNodeService;
+import org.dromara.workflow.utils.QueryUtils;
+import org.flowable.engine.TaskService;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * 浠诲姟绠$悊 鎺у埗灞�
+ *
+ * @author may
+ */
+@Validated
+@RequiredArgsConstructor
+@RestController
+@RequestMapping("/workflow/task")
+public class ActTaskController extends BaseController {
+
+ private final IActTaskService actTaskService;
+
+ private final TaskService taskService;
+
+ private final IWfTaskBackNodeService wfTaskBackNodeService;
+
+
+ /**
+ * 鍚姩浠诲姟
+ *
+ * @param startProcessBo 鍚姩娴佺▼鍙傛暟
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/startWorkFlow")
+ public R<Map<String, Object>> startWorkFlow(@Validated(AddGroup.class) @RequestBody StartProcessBo startProcessBo) {
+ Map<String, Object> map = actTaskService.startWorkFlow(startProcessBo);
+ return R.ok("鎻愪氦鎴愬姛", map);
+ }
+
+ /**
+ * 鍔炵悊浠诲姟
+ *
+ * @param completeTaskBo 鍔炵悊浠诲姟鍙傛暟
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/completeTask")
+ public R<Void> completeTask(@Validated(AddGroup.class) @RequestBody CompleteTaskBo completeTaskBo) {
+ return toAjax(actTaskService.completeTask(completeTaskBo));
+ }
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勫緟鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @GetMapping("/getPageByTaskWait")
+ public TableDataInfo<TaskVo> getPageByTaskWait(TaskBo taskBo, PageQuery pageQuery) {
+ return actTaskService.getPageByTaskWait(taskBo, pageQuery);
+ }
+
+ /**
+ * 鏌ヨ褰撳墠绉熸埛鎵�鏈夊緟鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @GetMapping("/getPageByAllTaskWait")
+ public TableDataInfo<TaskVo> getPageByAllTaskWait(TaskBo taskBo, PageQuery pageQuery) {
+ return actTaskService.getPageByAllTaskWait(taskBo, pageQuery);
+ }
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勫凡鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @GetMapping("/getPageByTaskFinish")
+ public TableDataInfo<TaskVo> getPageByTaskFinish(TaskBo taskBo, PageQuery pageQuery) {
+ return actTaskService.getPageByTaskFinish(taskBo, pageQuery);
+ }
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勬妱閫�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @GetMapping("/getPageByTaskCopy")
+ public TableDataInfo<TaskVo> getPageByTaskCopy(TaskBo taskBo, PageQuery pageQuery) {
+ return actTaskService.getPageByTaskCopy(taskBo, pageQuery);
+ }
+
+ /**
+ * 鏌ヨ褰撳墠绉熸埛鎵�鏈夊凡鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @GetMapping("/getPageByAllTaskFinish")
+ public TableDataInfo<TaskVo> getPageByAllTaskFinish(TaskBo taskBo, PageQuery pageQuery) {
+ return actTaskService.getPageByAllTaskFinish(taskBo, pageQuery);
+ }
+
+ /**
+ * 绛炬敹锛堟嬀鍙栵級浠诲姟
+ *
+ * @param taskId 浠诲姟id
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/claim/{taskId}")
+ public R<Void> claimTask(@NotBlank(message = "浠诲姟id涓嶈兘涓虹┖") @PathVariable String taskId) {
+ try {
+ taskService.claim(taskId, Convert.toStr(LoginHelper.getUserId()));
+ return R.ok();
+ } catch (Exception e) {
+ e.printStackTrace();
+ return R.fail("绛炬敹浠诲姟澶辫触锛�" + e.getMessage());
+ }
+ }
+
+ /**
+ * 褰掕繕锛堟嬀鍙栫殑锛変换鍔�
+ *
+ * @param taskId 浠诲姟id
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/returnTask/{taskId}")
+ public R<Void> returnTask(@NotBlank(message = "浠诲姟id涓嶈兘涓虹┖") @PathVariable String taskId) {
+ try {
+ taskService.setAssignee(taskId, null);
+ return R.ok();
+ } catch (Exception e) {
+ e.printStackTrace();
+ return R.fail("褰掕繕浠诲姟澶辫触锛�" + e.getMessage());
+ }
+ }
+
+ /**
+ * 濮旀淳浠诲姟
+ *
+ * @param delegateBo 鍙傛暟
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/delegateTask")
+ public R<Void> delegateTask(@Validated({AddGroup.class}) @RequestBody DelegateBo delegateBo) {
+ return toAjax(actTaskService.delegateTask(delegateBo));
+ }
+
+ /**
+ * 缁堟浠诲姟
+ *
+ * @param terminationBo 鍙傛暟
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.DELETE)
+ @RepeatSubmit()
+ @PostMapping("/terminationTask")
+ public R<Void> terminationTask(@RequestBody TerminationBo terminationBo) {
+ return toAjax(actTaskService.terminationTask(terminationBo));
+ }
+
+ /**
+ * 杞姙浠诲姟
+ *
+ * @param transmitBo 鍙傛暟
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/transferTask")
+ public R<Void> transferTask(@Validated({AddGroup.class}) @RequestBody TransmitBo transmitBo) {
+ return toAjax(actTaskService.transferTask(transmitBo));
+ }
+
+ /**
+ * 浼氱浠诲姟鍔犵
+ *
+ * @param addMultiBo 鍙傛暟
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/addMultiInstanceExecution")
+ public R<Void> addMultiInstanceExecution(@Validated({AddGroup.class}) @RequestBody AddMultiBo addMultiBo) {
+ return toAjax(actTaskService.addMultiInstanceExecution(addMultiBo));
+ }
+
+ /**
+ * 浼氱浠诲姟鍑忕
+ *
+ * @param deleteMultiBo 鍙傛暟
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/deleteMultiInstanceExecution")
+ public R<Void> deleteMultiInstanceExecution(@Validated({AddGroup.class}) @RequestBody DeleteMultiBo deleteMultiBo) {
+ return toAjax(actTaskService.deleteMultiInstanceExecution(deleteMultiBo));
+ }
+
+ /**
+ * 椹冲洖瀹℃壒
+ *
+ * @param backProcessBo 鍙傛暟
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/backProcess")
+ public R<String> backProcess(@Validated({AddGroup.class}) @RequestBody BackProcessBo backProcessBo) {
+ return R.ok(actTaskService.backProcess(backProcessBo));
+ }
+
+ /**
+ * 鑾峰彇褰撳墠浠诲姟
+ *
+ * @param taskId 浠诲姟id
+ */
+ @GetMapping("/getTaskById/{taskId}")
+ public R<TaskVo> getTaskById(@PathVariable String taskId) {
+ return R.ok(QueryUtils.getTask(taskId));
+ }
+
+
+ /**
+ * 淇敼浠诲姟鍔炵悊浜�
+ *
+ * @param taskIds 浠诲姟id
+ * @param userId 鍔炵悊浜篿d
+ */
+ @Log(title = "浠诲姟绠$悊", businessType = BusinessType.UPDATE)
+ @RepeatSubmit()
+ @PutMapping("/updateAssignee/{taskIds}/{userId}")
+ public R<Void> updateAssignee(@PathVariable String[] taskIds, @PathVariable String userId) {
+ return toAjax(actTaskService.updateAssignee(taskIds, userId));
+ }
+
+ /**
+ * 鏌ヨ娴佺▼鍙橀噺
+ *
+ * @param taskId 浠诲姟id
+ */
+ @GetMapping("/getInstanceVariable/{taskId}")
+ public R<List<VariableVo>> getProcessInstVariable(@PathVariable String taskId) {
+ return R.ok(actTaskService.getInstanceVariable(taskId));
+ }
+
+ /**
+ * 鑾峰彇鍙┏鍥炲緱浠诲姟鑺傜偣
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ @GetMapping("/getTaskNodeList/{processInstanceId}")
+ public R<List<WfTaskBackNode>> getNodeList(@PathVariable String processInstanceId) {
+ return R.ok(CollUtil.reverse(wfTaskBackNodeService.getListByInstanceId(processInstanceId)));
+ }
+
+ /**
+ * 鏌ヨ宸ヤ綔娴佷换鍔$敤鎴烽�夋嫨鍔犵浜哄憳
+ *
+ * @param taskId 浠诲姟id
+ */
+ @GetMapping("/getTaskUserIdsByAddMultiInstance/{taskId}")
+ public R<String> getTaskUserIdsByAddMultiInstance(@PathVariable String taskId) {
+ return R.ok(actTaskService.getTaskUserIdsByAddMultiInstance(taskId));
+ }
+
+ /**
+ * 鏌ヨ宸ヤ綔娴侀�夋嫨鍑忕浜哄憳
+ *
+ * @param taskId 浠诲姟id
+ */
+ @GetMapping("/getListByDeleteMultiInstance/{taskId}")
+ public R<List<TaskVo>> getListByDeleteMultiInstance(@PathVariable String taskId) {
+ return R.ok(actTaskService.getListByDeleteMultiInstance(taskId));
+ }
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/TestLeaveController.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/TestLeaveController.java
new file mode 100644
index 0000000..17b6755
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/TestLeaveController.java
@@ -0,0 +1,106 @@
+package org.dromara.workflow.controller;
+
+import cn.dev33.satoken.annotation.SaCheckPermission;
+import jakarta.servlet.http.HttpServletResponse;
+import jakarta.validation.constraints.NotEmpty;
+import jakarta.validation.constraints.NotNull;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.domain.R;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import org.dromara.common.excel.utils.ExcelUtil;
+import org.dromara.common.idempotent.annotation.RepeatSubmit;
+import org.dromara.common.log.annotation.Log;
+import org.dromara.common.log.enums.BusinessType;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.web.core.BaseController;
+import org.dromara.workflow.domain.bo.TestLeaveBo;
+import org.dromara.workflow.domain.vo.TestLeaveVo;
+import org.dromara.workflow.service.ITestLeaveService;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+
+/**
+ * 璇峰亣
+ *
+ * @author may
+ * @date 2023-07-21
+ */
+@Validated
+@RequiredArgsConstructor
+@RestController
+@RequestMapping("/demo/leave")
+public class TestLeaveController extends BaseController {
+
+ private final ITestLeaveService testLeaveService;
+
+ /**
+ * 鏌ヨ璇峰亣鍒楄〃
+ */
+ @SaCheckPermission("demo:leave:list")
+ @GetMapping("/list")
+ public TableDataInfo<TestLeaveVo> list(TestLeaveBo bo, PageQuery pageQuery) {
+ return testLeaveService.queryPageList(bo, pageQuery);
+ }
+
+ /**
+ * 瀵煎嚭璇峰亣鍒楄〃
+ */
+ @SaCheckPermission("demo:leave:export")
+ @Log(title = "璇峰亣", businessType = BusinessType.EXPORT)
+ @PostMapping("/export")
+ public void export(TestLeaveBo bo, HttpServletResponse response) {
+ List<TestLeaveVo> list = testLeaveService.queryList(bo);
+ ExcelUtil.exportExcel(list, "璇峰亣", TestLeaveVo.class, response);
+ }
+
+ /**
+ * 鑾峰彇璇峰亣璇︾粏淇℃伅
+ *
+ * @param id 涓婚敭
+ */
+ @SaCheckPermission("demo:leave:query")
+ @GetMapping("/{id}")
+ public R<TestLeaveVo> getInfo(@NotNull(message = "涓婚敭涓嶈兘涓虹┖")
+ @PathVariable Long id) {
+ return R.ok(testLeaveService.queryById(id));
+ }
+
+ /**
+ * 鏂板璇峰亣
+ */
+ @SaCheckPermission("demo:leave:add")
+ @Log(title = "璇峰亣", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping()
+ public R<TestLeaveVo> add(@Validated(AddGroup.class) @RequestBody TestLeaveBo bo) {
+ return R.ok(testLeaveService.insertByBo(bo));
+ }
+
+ /**
+ * 淇敼璇峰亣
+ */
+ @SaCheckPermission("demo:leave:edit")
+ @Log(title = "璇峰亣", businessType = BusinessType.UPDATE)
+ @RepeatSubmit()
+ @PutMapping()
+ public R<TestLeaveVo> edit(@Validated(EditGroup.class) @RequestBody TestLeaveBo bo) {
+ return R.ok(testLeaveService.updateByBo(bo));
+ }
+
+ /**
+ * 鍒犻櫎璇峰亣
+ *
+ * @param ids 涓婚敭涓�
+ */
+ @SaCheckPermission("demo:leave:remove")
+ @Log(title = "璇峰亣", businessType = BusinessType.DELETE)
+ @DeleteMapping("/{ids}")
+ public R<Void> remove(@NotEmpty(message = "涓婚敭涓嶈兘涓虹┖")
+ @PathVariable Long[] ids) {
+ return toAjax(testLeaveService.deleteWithValidByIds(List.of(ids)));
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfCategoryController.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfCategoryController.java
new file mode 100644
index 0000000..8dced89
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfCategoryController.java
@@ -0,0 +1,106 @@
+package org.dromara.workflow.controller;
+
+import cn.dev33.satoken.annotation.SaCheckPermission;
+import jakarta.servlet.http.HttpServletResponse;
+import jakarta.validation.constraints.NotEmpty;
+import jakarta.validation.constraints.NotNull;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.domain.R;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import org.dromara.common.excel.utils.ExcelUtil;
+import org.dromara.common.idempotent.annotation.RepeatSubmit;
+import org.dromara.common.log.annotation.Log;
+import org.dromara.common.log.enums.BusinessType;
+import org.dromara.common.web.core.BaseController;
+import org.dromara.workflow.domain.bo.WfCategoryBo;
+import org.dromara.workflow.domain.vo.WfCategoryVo;
+import org.dromara.workflow.service.IWfCategoryService;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+
+/**
+ * 娴佺▼鍒嗙被
+ *
+ * @author may
+ * @date 2023-06-28
+ */
+@Validated
+@RequiredArgsConstructor
+@RestController
+@RequestMapping("/workflow/category")
+public class WfCategoryController extends BaseController {
+
+ private final IWfCategoryService wfCategoryService;
+
+ /**
+ * 鏌ヨ娴佺▼鍒嗙被鍒楄〃
+ */
+ @SaCheckPermission("workflow:category:list")
+ @GetMapping("/list")
+ public R<List<WfCategoryVo>> list(WfCategoryBo bo) {
+ List<WfCategoryVo> list = wfCategoryService.queryList(bo);
+ return R.ok(list);
+
+ }
+
+ /**
+ * 瀵煎嚭娴佺▼鍒嗙被鍒楄〃
+ */
+ @SaCheckPermission("workflow:category:export")
+ @Log(title = "娴佺▼鍒嗙被", businessType = BusinessType.EXPORT)
+ @PostMapping("/export")
+ public void export(WfCategoryBo bo, HttpServletResponse response) {
+ List<WfCategoryVo> list = wfCategoryService.queryList(bo);
+ ExcelUtil.exportExcel(list, "娴佺▼鍒嗙被", WfCategoryVo.class, response);
+ }
+
+ /**
+ * 鑾峰彇娴佺▼鍒嗙被璇︾粏淇℃伅
+ *
+ * @param id 涓婚敭
+ */
+ @SaCheckPermission("workflow:category:query")
+ @GetMapping("/{id}")
+ public R<WfCategoryVo> getInfo(@NotNull(message = "涓婚敭涓嶈兘涓虹┖")
+ @PathVariable Long id) {
+ return R.ok(wfCategoryService.queryById(id));
+ }
+
+ /**
+ * 鏂板娴佺▼鍒嗙被
+ */
+ @SaCheckPermission("workflow:category:add")
+ @Log(title = "娴佺▼鍒嗙被", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping()
+ public R<Void> add(@Validated(AddGroup.class) @RequestBody WfCategoryBo bo) {
+ return toAjax(wfCategoryService.insertByBo(bo));
+ }
+
+ /**
+ * 淇敼娴佺▼鍒嗙被
+ */
+ @SaCheckPermission("workflow:category:edit")
+ @Log(title = "娴佺▼鍒嗙被", businessType = BusinessType.UPDATE)
+ @RepeatSubmit()
+ @PutMapping()
+ public R<Void> edit(@Validated(EditGroup.class) @RequestBody WfCategoryBo bo) {
+ return toAjax(wfCategoryService.updateByBo(bo));
+ }
+
+ /**
+ * 鍒犻櫎娴佺▼鍒嗙被
+ *
+ * @param ids 涓婚敭涓�
+ */
+ @SaCheckPermission("workflow:category:remove")
+ @Log(title = "娴佺▼鍒嗙被", businessType = BusinessType.DELETE)
+ @DeleteMapping("/{ids}")
+ public R<Void> remove(@NotEmpty(message = "涓婚敭涓嶈兘涓虹┖")
+ @PathVariable Long[] ids) {
+ return toAjax(wfCategoryService.deleteWithValidByIds(List.of(ids), true));
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfDefinitionConfigController.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfDefinitionConfigController.java
new file mode 100644
index 0000000..176aba2
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfDefinitionConfigController.java
@@ -0,0 +1,79 @@
+package org.dromara.workflow.controller;
+
+import java.util.List;
+
+import lombok.RequiredArgsConstructor;
+import jakarta.validation.constraints.*;
+import org.dromara.workflow.domain.bo.WfDefinitionConfigBo;
+import org.springframework.web.bind.annotation.*;
+import org.springframework.validation.annotation.Validated;
+import org.dromara.common.idempotent.annotation.RepeatSubmit;
+import org.dromara.common.log.annotation.Log;
+import org.dromara.common.web.core.BaseController;
+import org.dromara.common.core.domain.R;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.log.enums.BusinessType;
+import org.dromara.workflow.domain.vo.WfDefinitionConfigVo;
+import org.dromara.workflow.service.IWfDefinitionConfigService;
+
+/**
+ * 娴佺▼瀹氫箟閰嶇疆
+ *
+ * @author may
+ * @date 2024-03-18
+ */
+@Validated
+@RequiredArgsConstructor
+@RestController
+@RequestMapping("/workflow/definitionConfig")
+public class WfDefinitionConfigController extends BaseController {
+
+ private final IWfDefinitionConfigService wfDefinitionConfigService;
+
+
+ /**
+ * 鑾峰彇娴佺▼瀹氫箟閰嶇疆璇︾粏淇℃伅
+ *
+ * @param definitionId 涓婚敭
+ */
+ @GetMapping("/getByDefId/{definitionId}")
+ public R<WfDefinitionConfigVo> getByDefId(@NotBlank(message = "娴佺▼瀹氫箟ID涓嶈兘涓虹┖")
+ @PathVariable String definitionId) {
+ return R.ok(wfDefinitionConfigService.getByDefId(definitionId));
+ }
+
+ /**
+ * 鏂板娴佺▼瀹氫箟閰嶇疆
+ */
+ @Log(title = "娴佺▼瀹氫箟閰嶇疆", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping("/saveOrUpdate")
+ public R<Void> saveOrUpdate(@Validated(AddGroup.class) @RequestBody WfDefinitionConfigBo bo) {
+ return toAjax(wfDefinitionConfigService.saveOrUpdate(bo));
+ }
+
+ /**
+ * 鍒犻櫎娴佺▼瀹氫箟閰嶇疆
+ *
+ * @param ids 涓婚敭涓�
+ */
+ @Log(title = "娴佺▼瀹氫箟閰嶇疆", businessType = BusinessType.DELETE)
+ @DeleteMapping("/{ids}")
+ public R<Void> remove(@NotEmpty(message = "涓婚敭涓嶈兘涓虹┖")
+ @PathVariable Long[] ids) {
+ return toAjax(wfDefinitionConfigService.deleteByIds(List.of(ids)));
+ }
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆鎺掗櫎褰撳墠鏌ヨ鐨勬祦绋嬪畾涔�
+ *
+ * @param tableName 琛ㄥ悕
+ * @param definitionId 娴佺▼瀹氫箟id
+ */
+ @GetMapping("/getByTableNameNotDefId/{tableName}/{definitionId}")
+ public R<List<WfDefinitionConfigVo>> getByTableNameNotDefId(@NotBlank(message = "琛ㄥ悕涓嶈兘涓虹┖") @PathVariable String tableName,
+ @NotBlank(message = "娴佺▼瀹氫箟ID涓嶈兘涓虹┖") @PathVariable String definitionId) {
+ return R.ok(wfDefinitionConfigService.getByTableNameNotDefId(tableName, definitionId));
+ }
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfFormManageController.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfFormManageController.java
new file mode 100644
index 0000000..198e233
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/controller/WfFormManageController.java
@@ -0,0 +1,114 @@
+package org.dromara.workflow.controller;
+
+import java.util.List;
+
+import lombok.RequiredArgsConstructor;
+import jakarta.servlet.http.HttpServletResponse;
+import jakarta.validation.constraints.*;
+import cn.dev33.satoken.annotation.SaCheckPermission;
+import org.springframework.web.bind.annotation.*;
+import org.springframework.validation.annotation.Validated;
+import org.dromara.common.idempotent.annotation.RepeatSubmit;
+import org.dromara.common.log.annotation.Log;
+import org.dromara.common.web.core.BaseController;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.core.domain.R;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import org.dromara.common.log.enums.BusinessType;
+import org.dromara.common.excel.utils.ExcelUtil;
+import org.dromara.workflow.domain.vo.WfFormManageVo;
+import org.dromara.workflow.domain.bo.WfFormManageBo;
+import org.dromara.workflow.service.IWfFormManageService;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+
+/**
+ * 琛ㄥ崟绠$悊
+ *
+ * @author may
+ * @date 2024-03-29
+ */
+@Validated
+@RequiredArgsConstructor
+@RestController
+@RequestMapping("/workflow/formManage")
+public class WfFormManageController extends BaseController {
+
+ private final IWfFormManageService wfFormManageService;
+
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊鍒楄〃
+ */
+ @SaCheckPermission("workflow:formManage:list")
+ @GetMapping("/list")
+ public TableDataInfo<WfFormManageVo> list(WfFormManageBo bo, PageQuery pageQuery) {
+ return wfFormManageService.queryPageList(bo, pageQuery);
+ }
+
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊鍒楄〃
+ */
+ @SaCheckPermission("workflow:formManage:list")
+ @GetMapping("/list/selectList")
+ public R<List<WfFormManageVo>> selectList() {
+ return R.ok(wfFormManageService.selectList());
+ }
+
+ /**
+ * 瀵煎嚭琛ㄥ崟绠$悊鍒楄〃
+ */
+ @SaCheckPermission("workflow:formManage:export")
+ @Log(title = "琛ㄥ崟绠$悊", businessType = BusinessType.EXPORT)
+ @PostMapping("/export")
+ public void export(WfFormManageBo bo, HttpServletResponse response) {
+ List<WfFormManageVo> list = wfFormManageService.queryList(bo);
+ ExcelUtil.exportExcel(list, "琛ㄥ崟绠$悊", WfFormManageVo.class, response);
+ }
+
+ /**
+ * 鑾峰彇琛ㄥ崟绠$悊璇︾粏淇℃伅
+ *
+ * @param id 涓婚敭
+ */
+ @SaCheckPermission("workflow:formManage:query")
+ @GetMapping("/{id}")
+ public R<WfFormManageVo> getInfo(@NotNull(message = "涓婚敭涓嶈兘涓虹┖")
+ @PathVariable Long id) {
+ return R.ok(wfFormManageService.queryById(id));
+ }
+
+ /**
+ * 鏂板琛ㄥ崟绠$悊
+ */
+ @SaCheckPermission("workflow:formManage:add")
+ @Log(title = "琛ㄥ崟绠$悊", businessType = BusinessType.INSERT)
+ @RepeatSubmit()
+ @PostMapping()
+ public R<Void> add(@Validated(AddGroup.class) @RequestBody WfFormManageBo bo) {
+ return toAjax(wfFormManageService.insertByBo(bo));
+ }
+
+ /**
+ * 淇敼琛ㄥ崟绠$悊
+ */
+ @SaCheckPermission("workflow:formManage:edit")
+ @Log(title = "琛ㄥ崟绠$悊", businessType = BusinessType.UPDATE)
+ @RepeatSubmit()
+ @PutMapping()
+ public R<Void> edit(@Validated(EditGroup.class) @RequestBody WfFormManageBo bo) {
+ return toAjax(wfFormManageService.updateByBo(bo));
+ }
+
+ /**
+ * 鍒犻櫎琛ㄥ崟绠$悊
+ *
+ * @param ids 涓婚敭涓�
+ */
+ @SaCheckPermission("workflow:formManage:remove")
+ @Log(title = "琛ㄥ崟绠$悊", businessType = BusinessType.DELETE)
+ @DeleteMapping("/{ids}")
+ public R<Void> remove(@NotEmpty(message = "涓婚敭涓嶈兘涓虹┖")
+ @PathVariable Long[] ids) {
+ return toAjax(wfFormManageService.deleteByIds(List.of(ids)));
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/ActHiProcinst.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/ActHiProcinst.java
new file mode 100644
index 0000000..e87fb92
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/ActHiProcinst.java
@@ -0,0 +1,152 @@
+package org.dromara.workflow.domain;
+
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * 娴佺▼瀹炰緥瀵硅薄 act_hi_procinst
+ *
+ * @author may
+ * @date 2023-07-22
+ */
+@Data
+@TableName("act_hi_procinst")
+public class ActHiProcinst implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ *
+ */
+ @TableId(value = "ID_")
+ private String id;
+
+ /**
+ *
+ */
+ @TableField(value = "REV_")
+ private Long rev;
+
+ /**
+ *
+ */
+ @TableField(value = "PROC_INST_ID_")
+ private String procInstId;
+
+ /**
+ *
+ */
+ @TableField(value = "BUSINESS_KEY_")
+ private String businessKey;
+
+ /**
+ *
+ */
+ @TableField(value = "PROC_DEF_ID_")
+ private String procDefId;
+
+ /**
+ *
+ */
+ @TableField(value = "START_TIME_")
+ private Date startTime;
+
+ /**
+ *
+ */
+ @TableField(value = "END_TIME_")
+ private Date endTime;
+
+ /**
+ *
+ */
+ @TableField(value = "DURATION_")
+ private Long duration;
+
+ /**
+ *
+ */
+ @TableField(value = "START_USER_ID_")
+ private String startUserId;
+
+ /**
+ *
+ */
+ @TableField(value = "START_ACT_ID_")
+ private String startActId;
+
+ /**
+ *
+ */
+ @TableField(value = "END_ACT_ID_")
+ private String endActId;
+
+ /**
+ *
+ */
+ @TableField(value = "SUPER_PROCESS_INSTANCE_ID_")
+ private String superProcessInstanceId;
+
+ /**
+ *
+ */
+ @TableField(value = "DELETE_REASON_")
+ private String deleteReason;
+
+ /**
+ *
+ */
+ @TableField(value = "TENANT_ID_")
+ private String tenantId;
+
+ /**
+ *
+ */
+ @TableField(value = "NAME_")
+ private String name;
+
+ /**
+ *
+ */
+ @TableField(value = "CALLBACK_ID_")
+ private String callbackId;
+
+ /**
+ *
+ */
+ @TableField(value = "CALLBACK_TYPE_")
+ private String callbackType;
+
+ /**
+ *
+ */
+ @TableField(value = "REFERENCE_ID_")
+ private String referenceId;
+
+ /**
+ *
+ */
+ @TableField(value = "REFERENCE_TYPE_")
+ private String referenceType;
+
+ /**
+ *
+ */
+ @TableField(value = "PROPAGATED_STAGE_INST_ID_")
+ private String propagatedStageInstId;
+
+ /**
+ *
+ */
+ @TableField(value = "BUSINESS_STATUS_")
+ private String businessStatus;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/ActHiTaskinst.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/ActHiTaskinst.java
new file mode 100644
index 0000000..abc17b5
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/ActHiTaskinst.java
@@ -0,0 +1,193 @@
+package org.dromara.workflow.domain;
+
+import com.baomidou.mybatisplus.annotation.*;
+import lombok.Data;
+
+import java.io.Serializable;
+import java.util.Date;
+
+import java.io.Serial;
+
+/**
+ * 娴佺▼鍘嗗彶浠诲姟瀵硅薄 act_hi_taskinst
+ *
+ * @author may
+ * @date 2024-03-02
+ */
+@Data
+@TableName("act_hi_taskinst")
+public class ActHiTaskinst implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ *
+ */
+ @TableId(value = "ID_")
+ private String id;
+
+ /**
+ * 鐗堟湰
+ */
+ @TableField(value = "REV_")
+ private Long rev;
+
+ /**
+ * 娴佺▼瀹氫箟id
+ */
+ @TableField(value = "PROC_DEF_ID_")
+ private String procDefId;
+
+ /**
+ *
+ */
+ @TableField(value = "TASK_DEF_ID_")
+ private String taskDefId;
+
+ /**
+ * 浠诲姟鑺傜偣id
+ */
+ @TableField(value = "TASK_DEF_KEY_")
+ private String taskDefKey;
+
+ /**
+ * 娴佺▼瀹炰緥id
+ */
+ @TableField(value = "PROC_INST_ID_")
+ private String procInstId;
+
+ /**
+ * 娴佺▼鎵цid
+ */
+ @TableField(value = "EXECUTION_ID")
+ private String executionId;
+
+ /**
+ *
+ */
+ @TableField(value = "SCOPE_ID_")
+ private String scopeId;
+
+ /**
+ *
+ */
+ @TableField(value = "SUB_SCOPE_ID_")
+ private String subScopeId;
+
+ /**
+ * 鍏堢敤褰撳墠瀛楁鏍囪瘑鎶勯�佺被鍨�
+ */
+ @TableField(value = "SCOPE_TYPE_")
+ private String scopeType;
+
+ /**
+ *
+ */
+ @TableField(value = "SCOPE_DEFINITION_ID_")
+ private String scopeDefinitionId;
+
+ /**
+ *
+ */
+ @TableField(value = "PROPAGATED_STAGE_INST_ID_")
+ private String propagatedStageInstId;
+
+ /**
+ * 浠诲姟鍚嶇О
+ */
+ @TableField(value = "NAME_")
+ private String name;
+
+ /**
+ * 鐖剁骇id
+ */
+ @TableField(value = "PARENT_TASK_ID_")
+ private String parentTaskId;
+
+ /**
+ * 鎻忚堪
+ */
+ @TableField(value = "DESCRIPTION_")
+ private String description;
+
+ /**
+ * 鍔炵悊浜�
+ */
+ @TableField(value = "OWNER_")
+ private String owner;
+
+ /**
+ * 鍔炵悊浜�
+ */
+ @TableField(value = "ASSIGNEE_")
+ private String assignee;
+
+ /**
+ * 寮�濮嬩簨浠�
+ */
+ @TableField(value = "START_TIME_")
+ private Date startTime;
+
+ /**
+ * 璁ら鏃堕棿
+ */
+ @TableField(value = "CLAIM_TIME_")
+ private Date claimTime;
+
+ /**
+ * 缁撴潫鏃堕棿
+ */
+ @TableField(value = "END_TIME_")
+ private Date endTime;
+
+ /**
+ * 鎸佺画鏃堕棿
+ */
+ @TableField(value = "DURATION_")
+ private Long duration;
+
+ /**
+ * 鍒犻櫎鍘熷洜
+ */
+ @TableField(value = "DELETE_REASON_")
+ private String deleteReason;
+
+ /**
+ * 浼樺厛绾�
+ */
+ @TableField(value = "PRIORITY_")
+ private Long priority;
+
+ /**
+ * 鍒版湡鏃堕棿
+ */
+ @TableField(value = "DUE_DATE_")
+ private Date dueDate;
+
+ /**
+ *
+ */
+ @TableField(value = "FORM_KEY_")
+ private String formKey;
+
+ /**
+ * 鍒嗙被
+ */
+ @TableField(value = "CATEGORY_")
+ private String category;
+
+ /**
+ * 鏈�鍚庝慨鏀规椂闂�
+ */
+ @TableField(value = "LAST_UPDATED_TIME_")
+ private Date lastUpdatedTime;
+
+ /**
+ * 绉熸埛id
+ */
+ @TableField(value = "TENANT_ID_")
+ private String tenantId;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/TestLeave.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/TestLeave.java
new file mode 100644
index 0000000..0e26467
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/TestLeave.java
@@ -0,0 +1,58 @@
+package org.dromara.workflow.domain;
+
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import org.dromara.common.mybatis.core.domain.BaseEntity;
+
+import java.io.Serial;
+import java.util.Date;
+
+/**
+ * 璇峰亣瀵硅薄 test_leave
+ *
+ * @author may
+ * @date 2023-07-21
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@TableName("test_leave")
+public class TestLeave extends BaseEntity {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @TableId(value = "id")
+ private Long id;
+
+ /**
+ * 璇峰亣绫诲瀷
+ */
+ private String leaveType;
+
+ /**
+ * 寮�濮嬫椂闂�
+ */
+ private Date startDate;
+
+ /**
+ * 缁撴潫鏃堕棿
+ */
+ private Date endDate;
+
+ /**
+ * 璇峰亣澶╂暟
+ */
+ private Integer leaveDays;
+
+ /**
+ * 璇峰亣鍘熷洜
+ */
+ private String remark;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfCategory.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfCategory.java
new file mode 100644
index 0000000..94a7cf5
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfCategory.java
@@ -0,0 +1,52 @@
+package org.dromara.workflow.domain;
+
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import org.dromara.common.tenant.core.TenantEntity;
+
+import java.io.Serial;
+
+/**
+ * 娴佺▼鍒嗙被瀵硅薄 wf_category
+ *
+ * @author may
+ * @date 2023-06-27
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@TableName("wf_category")
+public class WfCategory extends TenantEntity {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @TableId(value = "id")
+ private Long id;
+
+ /**
+ * 鍒嗙被鍚嶇О
+ */
+ private String categoryName;
+
+ /**
+ * 鍒嗙被缂栫爜
+ */
+ private String categoryCode;
+
+ /**
+ * 鐖剁骇id
+ */
+ private Long parentId;
+
+ /**
+ * 鎺掑簭
+ */
+ private Long sortNum;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfDefinitionConfig.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfDefinitionConfig.java
new file mode 100644
index 0000000..11dcaa0
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfDefinitionConfig.java
@@ -0,0 +1,56 @@
+package org.dromara.workflow.domain;
+
+import org.dromara.common.mybatis.core.domain.BaseEntity;
+import com.baomidou.mybatisplus.annotation.*;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+import java.io.Serial;
+
+/**
+ * 娴佺▼瀹氫箟閰嶇疆瀵硅薄 wf_definition_config
+ *
+ * @author may
+ * @date 2024-03-18
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@TableName("wf_definition_config")
+public class WfDefinitionConfig extends BaseEntity {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @TableId(value = "id")
+ private Long id;
+
+ /**
+ * 琛ㄥ悕
+ */
+ private String tableName;
+
+ /**
+ * 娴佺▼瀹氫箟ID
+ */
+ private String definitionId;
+
+ /**
+ * 娴佺▼KEY
+ */
+ private String processKey;
+
+ /**
+ * 娴佺▼鐗堟湰
+ */
+ private Integer version;
+
+ /**
+ * 澶囨敞
+ */
+ private String remark;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfFormManage.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfFormManage.java
new file mode 100644
index 0000000..47f0d7a
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfFormManage.java
@@ -0,0 +1,51 @@
+package org.dromara.workflow.domain;
+
+import org.dromara.common.tenant.core.TenantEntity;
+import com.baomidou.mybatisplus.annotation.*;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+import java.io.Serial;
+
+/**
+ * 琛ㄥ崟绠$悊瀵硅薄 wf_form_manage
+ *
+ * @author may
+ * @date 2024-03-29
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@TableName("wf_form_manage")
+public class WfFormManage extends TenantEntity {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @TableId(value = "id")
+ private Long id;
+
+ /**
+ * 琛ㄥ崟鍚嶇О
+ */
+ private String formName;
+
+ /**
+ * 琛ㄥ崟绫诲瀷
+ */
+ private String formType;
+
+ /**
+ * 璺敱鍦板潃/琛ㄥ崟ID
+ */
+ private String router;
+
+ /**
+ * 澶囨敞
+ */
+ private String remark;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfNodeConfig.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfNodeConfig.java
new file mode 100644
index 0000000..999425f
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfNodeConfig.java
@@ -0,0 +1,61 @@
+package org.dromara.workflow.domain;
+
+import org.dromara.common.tenant.core.TenantEntity;
+import com.baomidou.mybatisplus.annotation.*;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+import java.io.Serial;
+
+/**
+ * 鑺傜偣閰嶇疆瀵硅薄 wf_node_config
+ *
+ * @author may
+ * @date 2024-03-30
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@TableName("wf_node_config")
+public class WfNodeConfig extends TenantEntity {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @TableId(value = "id")
+ private Long id;
+
+ /**
+ * 琛ㄥ崟id
+ */
+ private Long formId;
+
+ /**
+ * 琛ㄥ崟绫诲瀷
+ */
+ private String formType;
+
+ /**
+ * 鑺傜偣鍚嶇О
+ */
+ private String nodeName;
+
+ /**
+ * 鑺傜偣id
+ */
+ private String nodeId;
+
+ /**
+ * 娴佺▼瀹氫箟id
+ */
+ private String definitionId;
+
+ /**
+ * 鏄惁涓虹敵璇蜂汉鑺傜偣 锛�0鏄� 1鍚︼級
+ */
+ private String applyUserTask;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfTaskBackNode.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfTaskBackNode.java
new file mode 100644
index 0000000..6f59727
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/WfTaskBackNode.java
@@ -0,0 +1,61 @@
+package org.dromara.workflow.domain;
+
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import org.dromara.common.tenant.core.TenantEntity;
+
+import java.io.Serial;
+
+/**
+ * 鑺傜偣椹冲洖璁板綍 wf_task_back_node
+ *
+ * @author may
+ * @date 2024-03-13
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@TableName("wf_task_back_node")
+public class WfTaskBackNode extends TenantEntity {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @TableId(value = "id")
+ private Long id;
+
+ /**
+ * 瀹炰緥id
+ */
+ private String instanceId;
+
+ /**
+ * 鑺傜偣id
+ */
+ private String nodeId;
+
+ /**
+ * 鑺傜偣鍚嶇О
+ */
+ private String nodeName;
+
+ /**
+ * 鎺掑簭
+ */
+ private Integer orderNo;
+
+ /**
+ * 鑺傜偣绫诲瀷
+ */
+ private String taskType;
+
+ /**
+ * 鍔炵悊浜�
+ */
+ private String assignee;
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/AddMultiBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/AddMultiBo.java
new file mode 100644
index 0000000..320ec64
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/AddMultiBo.java
@@ -0,0 +1,40 @@
+package org.dromara.workflow.domain.bo;
+
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.NotEmpty;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * 鍔犵鍙傛暟璇锋眰
+ *
+ * @author may
+ */
+@Data
+public class AddMultiBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浠诲姟ID
+ */
+ @NotBlank(message = "浠诲姟ID涓嶈兘涓虹┖", groups = AddGroup.class)
+ private String taskId;
+
+ /**
+ * 鍔犵浜哄憳id
+ */
+ @NotEmpty(message = "鍔犵浜哄憳涓嶈兘涓虹┖", groups = AddGroup.class)
+ private List<Long> assignees;
+
+ /**
+ * 鍔犵浜哄憳鍚嶇О
+ */
+ @NotEmpty(message = "鍔犵浜哄憳涓嶈兘涓虹┖", groups = AddGroup.class)
+ private List<String> assigneeNames;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/BackProcessBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/BackProcessBo.java
new file mode 100644
index 0000000..d0f4369
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/BackProcessBo.java
@@ -0,0 +1,44 @@
+package org.dromara.workflow.domain.bo;
+
+import jakarta.validation.constraints.NotBlank;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.List;
+
+
+/**
+ * 椹冲洖鍙傛暟璇锋眰
+ *
+ * @author may
+ */
+@Data
+public class BackProcessBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浠诲姟ID
+ */
+ @NotBlank(message = "浠诲姟ID涓嶈兘涓虹┖", groups = AddGroup.class)
+ private String taskId;
+
+ /**
+ * 娑堟伅绫诲瀷
+ */
+ private List<String> messageType;
+
+ /**
+ * 椹冲洖鐨勮妭鐐筰d(鐩墠鏈娇鐢紝鐩存帴椹冲洖鍒扮敵璇蜂汉)
+ */
+ @NotBlank(message = "椹冲洖鐨勮妭鐐逛笉鑳戒负绌�", groups = AddGroup.class)
+ private String targetActivityId;
+
+ /**
+ * 鍔炵悊鎰忚
+ */
+ private String message;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/CompleteTaskBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/CompleteTaskBo.java
new file mode 100644
index 0000000..0623905
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/CompleteTaskBo.java
@@ -0,0 +1,65 @@
+package org.dromara.workflow.domain.bo;
+
+import jakarta.validation.constraints.NotBlank;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.workflow.domain.vo.WfCopy;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+
+/**
+ * 鍔炵悊浠诲姟璇锋眰瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class CompleteTaskBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浠诲姟id
+ */
+ @NotBlank(message = "浠诲姟id涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String taskId;
+
+ /**
+ * 闄勪欢id
+ */
+ private String fileId;
+
+ /**
+ * 鎶勯�佷汉鍛�
+ */
+ private List<WfCopy> wfCopyList;
+
+ /**
+ * 娑堟伅绫诲瀷
+ */
+ private List<String> messageType;
+
+ /**
+ * 鍔炵悊鎰忚
+ */
+ private String message;
+
+ /**
+ * 娴佺▼鍙橀噺
+ */
+ private Map<String, Object> variables;
+
+ public Map<String, Object> getVariables() {
+ if (variables == null) {
+ return new HashMap<>(16);
+ }
+ variables.entrySet().removeIf(entry -> Objects.isNull(entry.getValue()));
+ return variables;
+ }
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/DelegateBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/DelegateBo.java
new file mode 100644
index 0000000..a6846a6
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/DelegateBo.java
@@ -0,0 +1,38 @@
+package org.dromara.workflow.domain.bo;
+
+import jakarta.validation.constraints.NotBlank;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 濮旀淳浠诲姟璇锋眰瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class DelegateBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 濮旀淳浜篿d
+ */
+ @NotBlank(message = "濮旀淳浜篿d涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String userId;
+
+ /**
+ * 濮旀淳浜哄悕绉�
+ */
+ @NotBlank(message = "濮旀淳浜哄悕绉颁笉鑳戒负绌�", groups = {AddGroup.class})
+ private String nickName;
+
+ /**
+ * 浠诲姟id
+ */
+ @NotBlank(message = "浠诲姟id涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String taskId;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/DeleteMultiBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/DeleteMultiBo.java
new file mode 100644
index 0000000..e533167
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/DeleteMultiBo.java
@@ -0,0 +1,52 @@
+package org.dromara.workflow.domain.bo;
+
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.NotEmpty;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * 鍑忕鍙傛暟璇锋眰
+ *
+ * @author may
+ */
+@Data
+public class DeleteMultiBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浠诲姟ID
+ */
+ @NotBlank(message = "浠诲姟ID涓嶈兘涓虹┖", groups = AddGroup.class)
+ private String taskId;
+
+ /**
+ * 鍑忕浜哄憳
+ */
+ @NotEmpty(message = "鍑忕浜哄憳涓嶈兘涓虹┖", groups = AddGroup.class)
+ private List<String> taskIds;
+
+ /**
+ * 鎵цid
+ */
+ @NotEmpty(message = "鎵цid涓嶈兘涓虹┖", groups = AddGroup.class)
+ private List<String> executionIds;
+
+ /**
+ * 浜哄憳id
+ */
+ @NotEmpty(message = "鍑忕浜哄憳id涓嶈兘涓虹┖", groups = AddGroup.class)
+ private List<Long> assigneeIds;
+
+ /**
+ * 浜哄憳鍚嶇О
+ */
+ @NotEmpty(message = "鍑忕浜哄憳涓嶈兘涓虹┖", groups = AddGroup.class)
+ private List<String> assigneeNames;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ModelBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ModelBo.java
new file mode 100644
index 0000000..efe9acd
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ModelBo.java
@@ -0,0 +1,66 @@
+package org.dromara.workflow.domain.bo;
+
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.Pattern;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import org.dromara.workflow.common.constant.FlowConstant;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 妯″瀷璇锋眰瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class ModelBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 妯″瀷id
+ */
+ @NotBlank(message = "妯″瀷ID涓嶈兘涓虹┖", groups = {EditGroup.class})
+ private String id;
+
+ /**
+ * 妯″瀷鍚嶇О
+ */
+ @NotBlank(message = "妯″瀷鍚嶇О涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String name;
+
+ /**
+ * 妯″瀷鏍囪瘑key
+ */
+ @NotBlank(message = "妯″瀷鏍囪瘑key涓嶈兘涓虹┖", groups = {AddGroup.class})
+ @Pattern(regexp = FlowConstant.MODEL_KEY_PATTERN, message = "妯″瀷鏍囪瘑key鍙兘瀛楃鎴栬�呬笅鍒掔嚎寮�澶�", groups = {AddGroup.class})
+ private String key;
+
+ /**
+ * 妯″瀷鍒嗙被
+ */
+ @NotBlank(message = "妯″瀷鍒嗙被涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String categoryCode;
+
+ /**
+ * 妯″瀷XML
+ */
+ @NotBlank(message = "妯″瀷XML涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String xml;
+
+ /**
+ * 妯″瀷SVG鍥剧墖
+ */
+ @NotBlank(message = "妯″瀷SVG涓嶈兘涓虹┖", groups = {EditGroup.class})
+ private String svg;
+
+ /**
+ * 澶囨敞
+ */
+ private String description;
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessDefinitionBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessDefinitionBo.java
new file mode 100644
index 0000000..2025932
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessDefinitionBo.java
@@ -0,0 +1,34 @@
+package org.dromara.workflow.domain.bo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 娴佺▼瀹氫箟璇锋眰瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class ProcessDefinitionBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 娴佺▼瀹氫箟鍚嶇Оkey
+ */
+ private String key;
+
+ /**
+ * 娴佺▼瀹氫箟鍚嶇О
+ */
+ private String name;
+
+ /**
+ * 妯″瀷鍒嗙被
+ */
+ private String categoryCode;
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessInstanceBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessInstanceBo.java
new file mode 100644
index 0000000..2833b3e
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessInstanceBo.java
@@ -0,0 +1,43 @@
+package org.dromara.workflow.domain.bo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 娴佺▼瀹炰緥璇锋眰瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class ProcessInstanceBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 娴佺▼鍚嶇О
+ */
+ private String name;
+
+ /**
+ * 娴佺▼key
+ */
+ private String key;
+
+ /**
+ * 浠诲姟鍙戣捣浜�
+ */
+ private String startUserId;
+
+ /**
+ * 涓氬姟id
+ */
+ private String businessKey;
+
+ /**
+ * 妯″瀷鍒嗙被
+ */
+ private String categoryCode;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessInvalidBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessInvalidBo.java
new file mode 100644
index 0000000..35d5652
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/ProcessInvalidBo.java
@@ -0,0 +1,31 @@
+package org.dromara.workflow.domain.bo;
+
+import jakarta.validation.constraints.NotBlank;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 娴佺▼瀹炰緥浣滃簾璇锋眰瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class ProcessInvalidBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 娴佺▼瀹炰緥id
+ */
+ @NotBlank(message = "娴佺▼瀹炰緥id涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String processInstanceId;
+
+ /**
+ * 浣滃簾鍘熷洜
+ */
+ private String deleteReason;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/StartProcessBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/StartProcessBo.java
new file mode 100644
index 0000000..7af7935
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/StartProcessBo.java
@@ -0,0 +1,49 @@
+package org.dromara.workflow.domain.bo;
+
+
+import jakarta.validation.constraints.NotBlank;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Objects;
+
+/**
+ * 鍚姩娴佺▼瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class StartProcessBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓氬姟鍞竴鍊糹d
+ */
+ @NotBlank(message = "涓氬姟ID涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String businessKey;
+
+ /**
+ * 琛ㄥ悕
+ */
+ @NotBlank(message = "琛ㄥ悕涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String tableName;
+
+ /**
+ * 娴佺▼鍙橀噺锛屽墠绔細鎻愪氦涓�涓厓绱爗'entity': {涓氬姟璇︽儏鏁版嵁瀵硅薄}}
+ */
+ private Map<String, Object> variables;
+
+ public Map<String, Object> getVariables() {
+ if (variables == null) {
+ return new HashMap<>(16);
+ }
+ variables.entrySet().removeIf(entry -> Objects.isNull(entry.getValue()));
+ return variables;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/SysUserMultiBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/SysUserMultiBo.java
new file mode 100644
index 0000000..e4d99e4
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/SysUserMultiBo.java
@@ -0,0 +1,39 @@
+package org.dromara.workflow.domain.bo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+
+/**
+ * 鐢ㄦ埛鍔犵鏌ヨ
+ *
+ * @author may
+ */
+@Data
+public class SysUserMultiBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浜哄憳鍚嶇О
+ */
+ private String userName;
+
+ /**
+ * 浜哄憳鍚嶇О
+ */
+ private String nickName;
+
+ /**
+ * 閮ㄩ棬id
+ */
+ private String deptId;
+
+ /**
+ * 浠诲姟id
+ */
+ private String taskId;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TaskBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TaskBo.java
new file mode 100644
index 0000000..3037479
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TaskBo.java
@@ -0,0 +1,33 @@
+package org.dromara.workflow.domain.bo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 浠诲姟璇锋眰瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class TaskBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浠诲姟鍚嶇О
+ */
+ private String name;
+
+ /**
+ * 娴佺▼瀹氫箟鍚嶇О
+ */
+ private String processDefinitionName;
+
+ /**
+ * 娴佺▼瀹氫箟key
+ */
+ private String processDefinitionKey;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TaskUrgingBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TaskUrgingBo.java
new file mode 100644
index 0000000..20856ef
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TaskUrgingBo.java
@@ -0,0 +1,34 @@
+package org.dromara.workflow.domain.bo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * 浠诲姟鍌姙
+ *
+ * @author may
+ */
+@Data
+public class TaskUrgingBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 娴佺▼瀹炰緥id
+ */
+ private String processInstanceId;
+
+ /**
+ * 娑堟伅绫诲瀷
+ */
+ private List<String> messageType;
+
+ /**
+ * 鍌姙鍐呭锛堜负绌洪粯璁ょ郴缁熷唴缃俊鎭級
+ */
+ private String message;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TerminationBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TerminationBo.java
new file mode 100644
index 0000000..8f2206e
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TerminationBo.java
@@ -0,0 +1,31 @@
+package org.dromara.workflow.domain.bo;
+
+import jakarta.validation.constraints.NotBlank;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 缁堟浠诲姟璇锋眰瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class TerminationBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浠诲姟id
+ */
+ @NotBlank(message = "浠诲姟id涓虹┖", groups = AddGroup.class)
+ private String taskId;
+
+ /**
+ * 瀹℃壒鎰忚
+ */
+ private String comment;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TestLeaveBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TestLeaveBo.java
new file mode 100644
index 0000000..e71be59
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TestLeaveBo.java
@@ -0,0 +1,75 @@
+package org.dromara.workflow.domain.bo;
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.github.linpeilie.annotations.AutoMapper;
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.NotNull;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import org.dromara.common.mybatis.core.domain.BaseEntity;
+import org.dromara.workflow.domain.TestLeave;
+
+import java.util.Date;
+
+/**
+ * 璇峰亣涓氬姟瀵硅薄 test_leave
+ *
+ * @author may
+ * @date 2023-07-21
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@AutoMapper(target = TestLeave.class, reverseConvertGenerate = false)
+public class TestLeaveBo extends BaseEntity {
+
+ /**
+ * 涓婚敭
+ */
+ @NotNull(message = "涓婚敭涓嶈兘涓虹┖", groups = {EditGroup.class})
+ private Long id;
+
+ /**
+ * 璇峰亣绫诲瀷
+ */
+ @NotBlank(message = "璇峰亣绫诲瀷涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ private String leaveType;
+
+ /**
+ * 寮�濮嬫椂闂�
+ */
+ @NotNull(message = "寮�濮嬫椂闂翠笉鑳戒负绌�", groups = {AddGroup.class, EditGroup.class})
+ @JsonFormat(pattern = "yyyy-MM-dd")
+ private Date startDate;
+
+ /**
+ * 缁撴潫鏃堕棿
+ */
+ @NotNull(message = "缁撴潫鏃堕棿涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ @JsonFormat(pattern = "yyyy-MM-dd")
+ private Date endDate;
+
+ /**
+ * 璇峰亣澶╂暟
+ */
+ @NotNull(message = "璇峰亣澶╂暟涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ private Integer leaveDays;
+
+ /**
+ * 寮�濮嬫椂闂�
+ */
+ private Integer startLeaveDays;
+
+ /**
+ * 缁撴潫鏃堕棿
+ */
+ private Integer endLeaveDays;
+
+ /**
+ * 璇峰亣鍘熷洜
+ */
+ private String remark;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TransmitBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TransmitBo.java
new file mode 100644
index 0000000..3eb6609
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/TransmitBo.java
@@ -0,0 +1,37 @@
+package org.dromara.workflow.domain.bo;
+
+import jakarta.validation.constraints.NotBlank;
+import lombok.Data;
+import org.dromara.common.core.validate.AddGroup;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 缁堣浆鍔炲姟璇锋眰瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class TransmitBo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浠诲姟id
+ */
+ @NotBlank(message = "浠诲姟id涓虹┖", groups = AddGroup.class)
+ private String taskId;
+
+ /**
+ * 杞姙浜篿d
+ */
+ @NotBlank(message = "杞姙浜轰笉鑳戒负绌�", groups = AddGroup.class)
+ private String userId;
+
+ /**
+ * 瀹℃壒鎰忚
+ */
+ private String comment;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfCategoryBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfCategoryBo.java
new file mode 100644
index 0000000..69608fd
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfCategoryBo.java
@@ -0,0 +1,54 @@
+package org.dromara.workflow.domain.bo;
+
+import io.github.linpeilie.annotations.AutoMapper;
+import jakarta.validation.constraints.NotBlank;
+import jakarta.validation.constraints.NotNull;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import org.dromara.common.mybatis.core.domain.BaseEntity;
+import org.dromara.workflow.domain.WfCategory;
+
+/**
+ * 娴佺▼鍒嗙被涓氬姟瀵硅薄 wf_category
+ *
+ * @author may
+ * @date 2023-06-27
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@AutoMapper(target = WfCategory.class, reverseConvertGenerate = false)
+public class WfCategoryBo extends BaseEntity {
+
+ /**
+ * 涓婚敭
+ */
+ @NotNull(message = "涓婚敭涓嶈兘涓虹┖", groups = {EditGroup.class})
+ private Long id;
+
+ /**
+ * 鍒嗙被鍚嶇О
+ */
+ @NotBlank(message = "鍒嗙被鍚嶇О涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ private String categoryName;
+
+ /**
+ * 鍒嗙被缂栫爜
+ */
+ @NotBlank(message = "鍒嗙被缂栫爜涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ private String categoryCode;
+
+ /**
+ * 鐖剁骇id
+ */
+ @NotNull(message = "鐖剁骇id涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ private Long parentId;
+
+ /**
+ * 鎺掑簭
+ */
+ private Long sortNum;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfDefinitionConfigBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfDefinitionConfigBo.java
new file mode 100644
index 0000000..fac1770
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfDefinitionConfigBo.java
@@ -0,0 +1,59 @@
+package org.dromara.workflow.domain.bo;
+
+import org.dromara.workflow.domain.WfDefinitionConfig;
+import org.dromara.common.mybatis.core.domain.BaseEntity;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import io.github.linpeilie.annotations.AutoMapper;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import jakarta.validation.constraints.*;
+
+/**
+ * 娴佺▼瀹氫箟閰嶇疆涓氬姟瀵硅薄 wf_form_definition
+ *
+ * @author may
+ * @date 2024-03-18
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@AutoMapper(target = WfDefinitionConfig.class, reverseConvertGenerate = false)
+public class WfDefinitionConfigBo extends BaseEntity {
+
+ /**
+ * 涓婚敭
+ */
+ @NotNull(message = "涓婚敭涓嶈兘涓虹┖", groups = {EditGroup.class})
+ private Long id;
+
+ /**
+ * 琛ㄥ悕
+ */
+ @NotBlank(message = "琛ㄥ悕涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String tableName;
+
+ /**
+ * 娴佺▼瀹氫箟ID
+ */
+ @NotBlank(message = "娴佺▼瀹氫箟ID涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String definitionId;
+
+ /**
+ * 娴佺▼KEY
+ */
+ @NotBlank(message = "娴佺▼KEY涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private String processKey;
+
+ /**
+ * 娴佺▼鐗堟湰
+ */
+ @NotNull(message = "娴佺▼鐗堟湰涓嶈兘涓虹┖", groups = {AddGroup.class})
+ private Integer version;
+
+ /**
+ * 澶囨敞
+ */
+ private String remark;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfFormManageBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfFormManageBo.java
new file mode 100644
index 0000000..8afc286
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfFormManageBo.java
@@ -0,0 +1,53 @@
+package org.dromara.workflow.domain.bo;
+
+import org.dromara.workflow.domain.WfFormManage;
+import org.dromara.common.mybatis.core.domain.BaseEntity;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import io.github.linpeilie.annotations.AutoMapper;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import jakarta.validation.constraints.*;
+
+/**
+ * 琛ㄥ崟绠$悊涓氬姟瀵硅薄 wf_form_manage
+ *
+ * @author may
+ * @date 2024-03-29
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@AutoMapper(target = WfFormManage.class, reverseConvertGenerate = false)
+public class WfFormManageBo extends BaseEntity {
+
+ /**
+ * 涓婚敭
+ */
+ @NotNull(message = "涓婚敭涓嶈兘涓虹┖", groups = { EditGroup.class })
+ private Long id;
+
+ /**
+ * 琛ㄥ崟鍚嶇О
+ */
+ @NotBlank(message = "琛ㄥ崟鍚嶇О涓嶈兘涓虹┖", groups = { AddGroup.class, EditGroup.class })
+ private String formName;
+
+ /**
+ * 琛ㄥ崟绫诲瀷
+ */
+ @NotBlank(message = "琛ㄥ崟绫诲瀷涓嶈兘涓虹┖", groups = { AddGroup.class, EditGroup.class })
+ private String formType;
+ /**
+ * 璺敱鍦板潃/琛ㄥ崟ID
+ */
+ @NotBlank(message = "璺敱鍦板潃/琛ㄥ崟ID涓嶈兘涓虹┖", groups = { AddGroup.class, EditGroup.class })
+ private String router;
+
+
+ /**
+ * 澶囨敞
+ */
+ private String remark;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfNodeConfigBo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfNodeConfigBo.java
new file mode 100644
index 0000000..de518d3
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/bo/WfNodeConfigBo.java
@@ -0,0 +1,63 @@
+package org.dromara.workflow.domain.bo;
+
+import org.dromara.workflow.domain.WfNodeConfig;
+import org.dromara.common.mybatis.core.domain.BaseEntity;
+import org.dromara.common.core.validate.AddGroup;
+import org.dromara.common.core.validate.EditGroup;
+import io.github.linpeilie.annotations.AutoMapper;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import jakarta.validation.constraints.*;
+
+/**
+ * 鑺傜偣閰嶇疆涓氬姟瀵硅薄 wf_node_config
+ *
+ * @author may
+ * @date 2024-03-30
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+@AutoMapper(target = WfNodeConfig.class, reverseConvertGenerate = false)
+public class WfNodeConfigBo extends BaseEntity {
+
+ /**
+ * 涓婚敭
+ */
+ @NotNull(message = "涓婚敭涓嶈兘涓虹┖", groups = {EditGroup.class})
+ private Long id;
+
+ /**
+ * 琛ㄥ崟id
+ */
+ private Long formId;
+
+ /**
+ * 琛ㄥ崟绫诲瀷
+ */
+ private String formType;
+
+ /**
+ * 鑺傜偣鍚嶇О
+ */
+ @NotBlank(message = "鑺傜偣鍚嶇О涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ private String nodeName;
+
+ /**
+ * 鑺傜偣id
+ */
+ @NotBlank(message = "鑺傜偣id涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ private String nodeId;
+
+ /**
+ * 娴佺▼瀹氫箟id
+ */
+ @NotBlank(message = "娴佺▼瀹氫箟id涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ private String definitionId;
+
+ /**
+ * 鏄惁涓虹敵璇蜂汉鑺傜偣 锛�0鏄� 1鍚︼級
+ */
+ @NotBlank(message = "鏄惁涓虹敵璇蜂汉鑺傜偣涓嶈兘涓虹┖", groups = {AddGroup.class, EditGroup.class})
+ private String applyUserTask;
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ActHistoryInfoVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ActHistoryInfoVo.java
new file mode 100644
index 0000000..31b9722
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ActHistoryInfoVo.java
@@ -0,0 +1,89 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+import org.dromara.common.translation.annotation.Translation;
+import org.dromara.common.translation.constant.TransConstant;
+import org.flowable.engine.task.Attachment;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.Date;
+import java.util.List;
+
+/**
+ * 娴佺▼瀹℃壒璁板綍瑙嗗浘
+ *
+ * @author may
+ */
+@Data
+public class ActHistoryInfoVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+ /**
+ * 浠诲姟id
+ */
+ private String id;
+ /**
+ * 鑺傜偣id
+ */
+ private String taskDefinitionKey;
+ /**
+ * 浠诲姟鍚嶇О
+ */
+ private String name;
+ /**
+ * 娴佺▼瀹炰緥id
+ */
+ private String processInstanceId;
+ /**
+ * 寮�濮嬫椂闂�
+ */
+ private Date startTime;
+ /**
+ * 缁撴潫鏃堕棿
+ */
+ private Date endTime;
+ /**
+ * 杩愯鏃堕暱
+ */
+ private String runDuration;
+ /**
+ * 鐘舵��
+ */
+ private String status;
+ /**
+ * 鐘舵��
+ */
+ private String statusName;
+ /**
+ * 鍔炵悊浜篿d
+ */
+ private String assignee;
+
+ /**
+ * 鍔炵悊浜哄悕绉�
+ */
+ @Translation(type = TransConstant.USER_ID_TO_NICKNAME, mapper = "assignee")
+ private String nickName;
+
+ /**
+ * 鍔炵悊浜篿d
+ */
+ private String owner;
+
+ /**
+ * 瀹℃壒淇℃伅id
+ */
+ private String commentId;
+
+ /**
+ * 瀹℃壒淇℃伅
+ */
+ private String comment;
+
+ /**
+ * 瀹℃壒闄勪欢
+ */
+ private List<Attachment> attachmentList;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/GraphicInfoVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/GraphicInfoVo.java
new file mode 100644
index 0000000..7636131
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/GraphicInfoVo.java
@@ -0,0 +1,47 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 鑺傜偣鍥惧舰淇℃伅
+ *
+ * @author may
+ */
+@Data
+public class GraphicInfoVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+ /**
+ * x鍧愭爣
+ */
+ private double x;
+
+ /**
+ * y鍧愭爣
+ */
+ private double y;
+
+ /**
+ * 鑺傜偣楂樺害
+ */
+ private double height;
+
+ /**
+ * 鑺傜偣瀹藉害
+ */
+ private double width;
+
+ /**
+ * 鑺傜偣id
+ */
+ private String nodeId;
+
+ /**
+ * 鑺傜偣鍚嶇О
+ */
+ private String nodeName;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ModelVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ModelVo.java
new file mode 100644
index 0000000..b2ce811
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ModelVo.java
@@ -0,0 +1,48 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 妯″瀷瑙嗗浘瀵硅薄
+ *
+ * @author may
+ */
+@Data
+public class ModelVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 妯″瀷id
+ */
+ private String id;
+
+ /**
+ * 妯″瀷鍚嶇О
+ */
+ private String name;
+
+ /**
+ * 妯″瀷鏍囪瘑key
+ */
+ private String key;
+
+ /**
+ * 妯″瀷鍒嗙被
+ */
+ private String categoryCode;
+
+ /**
+ * 妯″瀷XML
+ */
+ private String xml;
+
+ /**
+ * 澶囨敞
+ */
+ private String description;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/MultiInstanceVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/MultiInstanceVo.java
new file mode 100644
index 0000000..b998396
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/MultiInstanceVo.java
@@ -0,0 +1,33 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 澶氬疄渚嬩俊鎭�
+ *
+ * @author may
+ */
+@Data
+public class MultiInstanceVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浼氱绫诲瀷锛堜覆琛岋紝骞惰锛�
+ */
+ private Object type;
+
+ /**
+ * 浼氱浜哄憳KEY
+ */
+ private String assignee;
+
+ /**
+ * 浼氱浜哄憳闆嗗悎KEY
+ */
+ private String assigneeList;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ParticipantVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ParticipantVo.java
new file mode 100644
index 0000000..c5876f6
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ParticipantVo.java
@@ -0,0 +1,43 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * 鍙備笌鑰�
+ *
+ * @author may
+ */
+@Data
+public class ParticipantVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 缁刬d锛堣鑹瞚d锛�
+ */
+ private List<Long> groupIds;
+
+ /**
+ * 鍊欓�変汉id锛堢敤鎴穒d锛� 褰撶粍id涓嶄负绌烘椂锛屽皢缁勫唴浜哄憳鏌ュ嚭鏀惧叆candidate
+ */
+ private List<Long> candidate;
+
+ /**
+ * 鍊欓�変汉鍚嶇О锛堢敤鎴峰悕绉帮級 褰撶粍id涓嶄负绌烘椂锛屽皢缁勫唴浜哄憳鏌ュ嚭鏀惧叆candidateName
+ */
+ private List<String> candidateName;
+
+ /**
+ * 鏄惁璁ら鏍囪瘑
+ * 褰撲负绌烘椂榛樿褰撳墠浠诲姟涓嶉渶瑕佽棰�
+ * 褰撲负true鏃跺綋鍓嶄换鍔¤鏄庝负鍊欓�夋ā寮忓苟涓旀湁浜哄凡缁忚棰嗕簡浠诲姟鍙互褰掕繕锛�
+ * 褰撲负false鏃跺綋鍓嶄换鍔¤鏄庝负鍊欓�夋ā寮忚浠诲姟鏈棰嗭紝
+ */
+ private Boolean claim;
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ProcessDefinitionVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ProcessDefinitionVo.java
new file mode 100644
index 0000000..034adbb
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ProcessDefinitionVo.java
@@ -0,0 +1,70 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * 娴佺▼瀹氫箟瑙嗗浘
+ *
+ * @author may
+ */
+@Data
+public class ProcessDefinitionVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 娴佺▼瀹氫箟id
+ */
+ private String id;
+
+ /**
+ * 娴佺▼瀹氫箟鍚嶇О
+ */
+ private String name;
+
+ /**
+ * 娴佺▼瀹氫箟鏍囪瘑key
+ */
+ private String key;
+
+ /**
+ * 娴佺▼瀹氫箟鐗堟湰
+ */
+ private int version;
+
+ /**
+ * 娴佺▼瀹氫箟鎸傝捣鎴栨縺娲� 1婵�娲� 2鎸傝捣
+ */
+ private int suspensionState;
+
+ /**
+ * 娴佺▼xml鍚嶇О
+ */
+ private String resourceName;
+
+ /**
+ * 娴佺▼鍥剧墖鍚嶇О
+ */
+ private String diagramResourceName;
+
+ /**
+ * 娴佺▼閮ㄧ讲id
+ */
+ private String deploymentId;
+
+ /**
+ * 娴佺▼閮ㄧ讲鏃堕棿
+ */
+ private Date deploymentTime;
+
+ /**
+ * 娴佺▼瀹氫箟閰嶇疆
+ */
+ private WfDefinitionConfigVo wfDefinitionConfigVo;
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ProcessInstanceVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ProcessInstanceVo.java
new file mode 100644
index 0000000..ab3e7a1
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/ProcessInstanceVo.java
@@ -0,0 +1,100 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.Date;
+import java.util.List;
+
+/**
+ * 娴佺▼瀹炰緥瑙嗗浘
+ *
+ * @author may
+ */
+@Data
+public class ProcessInstanceVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 娴佺▼瀹炰緥id
+ */
+ private String id;
+
+ /**
+ * 娴佺▼瀹氫箟id
+ */
+ private String processDefinitionId;
+
+ /**
+ * 娴佺▼瀹氫箟鍚嶇О
+ */
+ private String processDefinitionName;
+
+ /**
+ * 娴佺▼瀹氫箟key
+ */
+ private String processDefinitionKey;
+
+ /**
+ * 娴佺▼瀹氫箟鐗堟湰
+ */
+ private Integer processDefinitionVersion;
+
+ /**
+ * 閮ㄧ讲id
+ */
+ private String deploymentId;
+
+ /**
+ * 涓氬姟id
+ */
+ private String businessKey;
+
+ /**
+ * 鏄惁鎸傝捣
+ */
+ private Boolean isSuspended;
+
+ /**
+ * 绉熸埛id
+ */
+ private String tenantId;
+
+ /**
+ * 鍚姩鏃堕棿
+ */
+ private Date startTime;
+
+ /**
+ * 缁撴潫鏃堕棿
+ */
+ private Date endTime;
+
+ /**
+ * 鍚姩浜篿d
+ */
+ private String startUserId;
+
+ /**
+ * 娴佺▼鐘舵��
+ */
+ private String businessStatus;
+
+ /**
+ * 娴佺▼鐘舵��
+ */
+ private String businessStatusName;
+
+ /**
+ * 寰呭姙浠诲姟闆嗗悎
+ */
+ private List<TaskVo> taskVoList;
+
+ /**
+ * 鑺傜偣閰嶇疆
+ */
+ private WfNodeConfigVo wfNodeConfigVo;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/TaskVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/TaskVo.java
new file mode 100644
index 0000000..466e776
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/TaskVo.java
@@ -0,0 +1,173 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+import org.dromara.common.translation.annotation.Translation;
+import org.dromara.common.translation.constant.TransConstant;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * 浠诲姟瑙嗗浘
+ *
+ * @author may
+ */
+@Data
+public class TaskVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 浠诲姟id
+ */
+ private String id;
+
+ /**
+ * 浠诲姟鍚嶇О
+ */
+ private String name;
+
+ /**
+ * 鎻忚堪
+ */
+ private String description;
+
+ /**
+ * 浼樺厛绾�
+ */
+ private Integer priority;
+
+ /**
+ * 璐熻矗姝や换鍔$殑浜哄憳鐨勭敤鎴穒d
+ */
+ private String owner;
+
+ /**
+ * 鍔炵悊浜篿d
+ */
+ private Long assignee;
+
+ /**
+ * 鍔炵悊浜�
+ */
+ @Translation(type = TransConstant.USER_ID_TO_NICKNAME, mapper = "assignee")
+ private String assigneeName;
+
+
+ /**
+ * 娴佺▼瀹炰緥id
+ */
+ private String processInstanceId;
+
+ /**
+ * 鎵цid
+ */
+ private String executionId;
+
+ /**
+ * 鏃犵敤
+ */
+ private String taskDefinitionId;
+
+ /**
+ * 娴佺▼瀹氫箟id
+ */
+ private String processDefinitionId;
+
+ /**
+ * 鍒涘缓鏃堕棿
+ */
+ private Date createTime;
+
+ /**
+ * 宸插姙浠诲姟-鍒涘缓鏃堕棿
+ */
+ private Date startTime;
+
+ /**
+ * 缁撴潫鏃堕棿
+ */
+ private Date endTime;
+
+ /**
+ * 鑺傜偣id
+ */
+ private String taskDefinitionKey;
+
+ /**
+ * 浠诲姟鎴鏃ユ湡
+ */
+ private Date dueDate;
+
+ /**
+ * 娴佺▼绫诲埆
+ */
+ private String category;
+
+ /**
+ * 鐖剁骇浠诲姟id
+ */
+ private String parentTaskId;
+
+ /**
+ * 绉熸埛id
+ */
+ private String tenantId;
+
+ /**
+ * 璁ら鏃堕棿
+ */
+ private Date claimTime;
+
+ /**
+ * 娴佺▼鐘舵��
+ */
+ private String businessStatus;
+
+ /**
+ * 娴佺▼鐘舵��
+ */
+ private String businessStatusName;
+
+ /**
+ * 娴佺▼瀹氫箟鍚嶇О
+ */
+ private String processDefinitionName;
+
+ /**
+ * 娴佺▼瀹氫箟key
+ */
+ private String processDefinitionKey;
+
+ /**
+ * 娴佺▼瀹氫箟鐗堟湰
+ */
+ private Integer processDefinitionVersion;
+
+ /**
+ * 鍙備笌鑰�
+ */
+ private ParticipantVo participantVo;
+
+ /**
+ * 鏄惁浼氱
+ */
+ private Boolean multiInstance;
+
+ /**
+ * 涓氬姟id
+ */
+ private String businessKey;
+
+ /**
+ * 娴佺▼瀹氫箟閰嶇疆
+ */
+ private WfDefinitionConfigVo wfDefinitionConfigVo;
+
+ /**
+ * 鑺傜偣閰嶇疆
+ */
+ private WfNodeConfigVo wfNodeConfigVo;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/TestLeaveVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/TestLeaveVo.java
new file mode 100644
index 0000000..c62a356
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/TestLeaveVo.java
@@ -0,0 +1,70 @@
+package org.dromara.workflow.domain.vo;
+
+import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
+import com.alibaba.excel.annotation.ExcelProperty;
+import io.github.linpeilie.annotations.AutoMapper;
+import lombok.Data;
+import org.dromara.workflow.domain.TestLeave;
+
+import java.io.Serial;
+import java.io.Serializable;
+import java.util.Date;
+
+
+/**
+ * 璇峰亣瑙嗗浘瀵硅薄 test_leave
+ *
+ * @author may
+ * @date 2023-07-21
+ */
+@Data
+@ExcelIgnoreUnannotated
+@AutoMapper(target = TestLeave.class)
+public class TestLeaveVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @ExcelProperty(value = "涓婚敭")
+ private Long id;
+
+ /**
+ * 璇峰亣绫诲瀷
+ */
+ @ExcelProperty(value = "璇峰亣绫诲瀷")
+ private String leaveType;
+
+ /**
+ * 寮�濮嬫椂闂�
+ */
+ @ExcelProperty(value = "寮�濮嬫椂闂�")
+ private Date startDate;
+
+ /**
+ * 缁撴潫鏃堕棿
+ */
+ @ExcelProperty(value = "缁撴潫鏃堕棿")
+ private Date endDate;
+
+ /**
+ * 璇峰亣澶╂暟
+ */
+ @ExcelProperty(value = "璇峰亣澶╂暟")
+ private Integer leaveDays;
+
+ /**
+ * 澶囨敞
+ */
+ @ExcelProperty(value = "璇峰亣鍘熷洜")
+ private String remark;
+
+ /**
+ * 娴佺▼瀹炰緥瀵硅薄
+ */
+ private ProcessInstanceVo processInstanceVo;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/VariableVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/VariableVo.java
new file mode 100644
index 0000000..6a26c82
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/VariableVo.java
@@ -0,0 +1,28 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 娴佺▼鍙橀噺
+ *
+ * @author may
+ */
+@Data
+public class VariableVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 鍙橀噺key
+ */
+ private String key;
+
+ /**
+ * 鍙橀噺鍊�
+ */
+ private String value;
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfCategoryVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfCategoryVo.java
new file mode 100644
index 0000000..362f646
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfCategoryVo.java
@@ -0,0 +1,58 @@
+package org.dromara.workflow.domain.vo;
+
+import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
+import com.alibaba.excel.annotation.ExcelProperty;
+import io.github.linpeilie.annotations.AutoMapper;
+import lombok.Data;
+import org.dromara.workflow.domain.WfCategory;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+
+/**
+ * 娴佺▼鍒嗙被瑙嗗浘瀵硅薄 wf_category
+ *
+ * @author may
+ * @date 2023-06-27
+ */
+@Data
+@ExcelIgnoreUnannotated
+@AutoMapper(target = WfCategory.class)
+public class WfCategoryVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @ExcelProperty(value = "涓婚敭")
+ private Long id;
+
+ /**
+ * 鍒嗙被鍚嶇О
+ */
+ @ExcelProperty(value = "鍒嗙被鍚嶇О")
+ private String categoryName;
+
+ /**
+ * 鍒嗙被缂栫爜
+ */
+ @ExcelProperty(value = "鍒嗙被缂栫爜")
+ private String categoryCode;
+
+ /**
+ * 鐖剁骇id
+ */
+ @ExcelProperty(value = "鐖剁骇id")
+ private Long parentId;
+
+ /**
+ * 鎺掑簭
+ */
+ @ExcelProperty(value = "鎺掑簭")
+ private Long sortNum;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfCopy.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfCopy.java
new file mode 100644
index 0000000..88a5a21
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfCopy.java
@@ -0,0 +1,29 @@
+package org.dromara.workflow.domain.vo;
+
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+/**
+ * 鎶勯��
+ *
+ * @author may
+ */
+@Data
+public class WfCopy implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 鐢ㄦ埛id
+ */
+ private Long userId;
+
+ /**
+ * 鐢ㄦ埛鍚嶇О
+ */
+ private String userName;
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfDefinitionConfigVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfDefinitionConfigVo.java
new file mode 100644
index 0000000..9c7b0d7
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfDefinitionConfigVo.java
@@ -0,0 +1,70 @@
+package org.dromara.workflow.domain.vo;
+
+import org.dromara.workflow.domain.WfDefinitionConfig;
+import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
+import com.alibaba.excel.annotation.ExcelProperty;
+import io.github.linpeilie.annotations.AutoMapper;
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+
+/**
+ * 娴佺▼瀹氫箟閰嶇疆瑙嗗浘瀵硅薄 wf_definition_config
+ *
+ * @author may
+ * @date 2024-03-18
+ */
+@Data
+@ExcelIgnoreUnannotated
+@AutoMapper(target = WfDefinitionConfig.class)
+public class WfDefinitionConfigVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @ExcelProperty(value = "涓婚敭")
+ private Long id;
+
+ /**
+ * 琛ㄥ悕
+ */
+ @ExcelProperty(value = "琛ㄥ悕")
+ private String tableName;
+
+ /**
+ * 娴佺▼瀹氫箟ID
+ */
+ @ExcelProperty(value = "娴佺▼瀹氫箟ID")
+ private String definitionId;
+
+ /**
+ * 娴佺▼KEY
+ */
+ @ExcelProperty(value = "娴佺▼KEY")
+ private String processKey;
+
+
+ /**
+ * 娴佺▼鐗堟湰
+ */
+ @ExcelProperty(value = "娴佺▼鐗堟湰")
+ private Integer version;
+
+ /**
+ * 澶囨敞
+ */
+ @ExcelProperty(value = "澶囨敞")
+ private String remark;
+
+ /**
+ * 琛ㄥ崟绠$悊
+ */
+ private WfFormManageVo wfFormManageVo;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfFormManageVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfFormManageVo.java
new file mode 100644
index 0000000..302df23
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfFormManageVo.java
@@ -0,0 +1,63 @@
+package org.dromara.workflow.domain.vo;
+
+import org.dromara.workflow.domain.WfFormManage;
+import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
+import com.alibaba.excel.annotation.ExcelProperty;
+import io.github.linpeilie.annotations.AutoMapper;
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+
+/**
+ * 琛ㄥ崟绠$悊瑙嗗浘瀵硅薄 wf_form_manage
+ *
+ * @author may
+ * @date 2024-03-29
+ */
+@Data
+@ExcelIgnoreUnannotated
+@AutoMapper(target = WfFormManage.class)
+public class WfFormManageVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @ExcelProperty(value = "涓婚敭")
+ private Long id;
+
+ /**
+ * 琛ㄥ崟鍚嶇О
+ */
+ @ExcelProperty(value = "琛ㄥ崟鍚嶇О")
+ private String formName;
+
+ /**
+ * 琛ㄥ崟绫诲瀷
+ */
+ @ExcelProperty(value = "琛ㄥ崟绫诲瀷")
+ private String formType;
+
+ /**
+ * 琛ㄥ崟绫诲瀷鍚嶇О
+ */
+ private String formTypeName;
+
+ /**
+ * 璺敱鍦板潃/琛ㄥ崟ID
+ */
+ @ExcelProperty(value = "璺敱鍦板潃/琛ㄥ崟ID")
+ private String router;
+
+ /**
+ * 澶囨敞
+ */
+ @ExcelProperty(value = "澶囨敞")
+ private String remark;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfNodeConfigVo.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfNodeConfigVo.java
new file mode 100644
index 0000000..89e9d9b
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/domain/vo/WfNodeConfigVo.java
@@ -0,0 +1,75 @@
+package org.dromara.workflow.domain.vo;
+
+import org.dromara.workflow.domain.WfNodeConfig;
+import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
+import com.alibaba.excel.annotation.ExcelProperty;
+import io.github.linpeilie.annotations.AutoMapper;
+import lombok.Data;
+
+import java.io.Serial;
+import java.io.Serializable;
+
+
+/**
+ * 鑺傜偣閰嶇疆瑙嗗浘瀵硅薄 wf_node_config
+ *
+ * @author may
+ * @date 2024-03-30
+ */
+@Data
+@ExcelIgnoreUnannotated
+@AutoMapper(target = WfNodeConfig.class)
+public class WfNodeConfigVo implements Serializable {
+
+ @Serial
+ private static final long serialVersionUID = 1L;
+
+ /**
+ * 涓婚敭
+ */
+ @ExcelProperty(value = "涓婚敭")
+ private Long id;
+
+ /**
+ * 琛ㄥ崟id
+ */
+ @ExcelProperty(value = "琛ㄥ崟id")
+ private Long formId;
+
+ /**
+ * 琛ㄥ崟绫诲瀷
+ */
+ @ExcelProperty(value = "琛ㄥ崟绫诲瀷")
+ private String formType;
+
+ /**
+ * 鑺傜偣鍚嶇О
+ */
+ @ExcelProperty(value = "鑺傜偣鍚嶇О")
+ private String nodeName;
+
+ /**
+ * 鑺傜偣id
+ */
+ @ExcelProperty(value = "鑺傜偣id")
+ private String nodeId;
+
+ /**
+ * 娴佺▼瀹氫箟id
+ */
+ @ExcelProperty(value = "娴佺▼瀹氫箟id")
+ private String definitionId;
+
+ /**
+ * 鏄惁涓虹敵璇蜂汉鑺傜偣 锛�0鏄� 1鍚︼級
+ */
+ @ExcelProperty(value = "鏄惁涓虹敵璇蜂汉鑺傜偣 锛�0鏄� 1鍚︼級")
+ private String applyUserTask;
+
+ /**
+ * 琛ㄥ崟绠$悊
+ */
+ private WfFormManageVo wfFormManageVo;
+
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/CustomDefaultProcessDiagramCanvas.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/CustomDefaultProcessDiagramCanvas.java
new file mode 100644
index 0000000..39fd9d3
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/CustomDefaultProcessDiagramCanvas.java
@@ -0,0 +1,108 @@
+package org.dromara.workflow.flowable;
+
+import org.flowable.bpmn.model.AssociationDirection;
+import org.flowable.image.impl.DefaultProcessDiagramCanvas;
+
+import java.awt.*;
+import java.awt.geom.Line2D;
+import java.awt.geom.RoundRectangle2D;
+
+public class CustomDefaultProcessDiagramCanvas extends DefaultProcessDiagramCanvas {
+ //璁剧疆楂樹寒绾跨殑棰滆壊 杩欓噷鎴戣缃垚缁胯壊
+ protected static Color HIGHLIGHT_SEQUENCEFLOW_COLOR = Color.GREEN;
+
+ public CustomDefaultProcessDiagramCanvas(int width, int height, int minX, int minY, String imageType, String activityFontName, String labelFontName, String annotationFontName, ClassLoader customClassLoader) {
+ super(width, height, minX, minY, imageType, activityFontName, labelFontName, annotationFontName, customClassLoader);
+ }
+
+ /**
+ * 鐢荤嚎棰滆壊璁剧疆
+ */
+ public void drawConnection(int[] xPoints, int[] yPoints, boolean conditional, boolean isDefault, String connectionType,
+ AssociationDirection associationDirection, boolean highLighted, double scaleFactor) {
+
+ Paint originalPaint = g.getPaint();
+ Stroke originalStroke = g.getStroke();
+
+ g.setPaint(CONNECTION_COLOR);
+ if (connectionType.equals("association")) {
+ g.setStroke(ASSOCIATION_STROKE);
+ } else if (highLighted) {
+ //璁剧疆绾跨殑棰滆壊
+ g.setPaint(HIGHLIGHT_SEQUENCEFLOW_COLOR);
+ g.setStroke(HIGHLIGHT_FLOW_STROKE);
+ }
+
+ for (int i = 1; i < xPoints.length; i++) {
+ Integer sourceX = xPoints[i - 1];
+ Integer sourceY = yPoints[i - 1];
+ Integer targetX = xPoints[i];
+ Integer targetY = yPoints[i];
+ Line2D.Double line = new Line2D.Double(sourceX, sourceY, targetX, targetY);
+ g.draw(line);
+ }
+
+ if (isDefault) {
+ Line2D.Double line = new Line2D.Double(xPoints[0], yPoints[0], xPoints[1], yPoints[1]);
+ drawDefaultSequenceFlowIndicator(line, scaleFactor);
+ }
+
+ if (conditional) {
+ Line2D.Double line = new Line2D.Double(xPoints[0], yPoints[0], xPoints[1], yPoints[1]);
+ drawConditionalSequenceFlowIndicator(line, scaleFactor);
+ }
+
+ if (associationDirection == AssociationDirection.ONE || associationDirection == AssociationDirection.BOTH) {
+ Line2D.Double line = new Line2D.Double(xPoints[xPoints.length - 2], yPoints[xPoints.length - 2], xPoints[xPoints.length - 1], yPoints[xPoints.length - 1]);
+ drawArrowHead(line, scaleFactor);
+ }
+ if (associationDirection == AssociationDirection.BOTH) {
+ Line2D.Double line = new Line2D.Double(xPoints[1], yPoints[1], xPoints[0], yPoints[0]);
+ drawArrowHead(line, scaleFactor);
+ }
+ g.setPaint(originalPaint);
+ g.setStroke(originalStroke);
+ }
+
+ /**
+ * 楂樹寒鑺傜偣璁剧疆
+ */
+ public void drawHighLight(int x, int y, int width, int height) {
+ Paint originalPaint = g.getPaint();
+ Stroke originalStroke = g.getStroke();
+ //璁剧疆楂樹寒鑺傜偣鐨勯鑹�
+ g.setPaint(HIGHLIGHT_COLOR);
+ g.setStroke(THICK_TASK_BORDER_STROKE);
+
+ RoundRectangle2D rect = new RoundRectangle2D.Double(x, y, width, height, 20, 20);
+ g.draw(rect);
+
+ g.setPaint(originalPaint);
+ g.setStroke(originalStroke);
+ }
+
+ /**
+ * @description: 楂樹寒鑺傜偣绾㈣壊
+ * @param: x
+ * @param: y
+ * @param: width
+ * @param: height
+ * @return: void
+ * @author: gssong
+ * @date: 2022/4/12
+ */
+ public void drawHighLightRed(int x, int y, int width, int height) {
+ Paint originalPaint = g.getPaint();
+ Stroke originalStroke = g.getStroke();
+ //璁剧疆楂樹寒鑺傜偣鐨勯鑹�
+ g.setPaint(Color.green);
+ g.setStroke(THICK_TASK_BORDER_STROKE);
+
+ RoundRectangle2D rect = new RoundRectangle2D.Double(x, y, width, height, 20, 20);
+ g.draw(rect);
+
+ g.setPaint(originalPaint);
+ g.setStroke(originalStroke);
+ }
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/CustomDefaultProcessDiagramGenerator.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/CustomDefaultProcessDiagramGenerator.java
new file mode 100644
index 0000000..e4793a2
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/CustomDefaultProcessDiagramGenerator.java
@@ -0,0 +1,1120 @@
+/* Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.dromara.workflow.flowable;
+
+import org.flowable.bpmn.model.Event;
+import org.flowable.bpmn.model.Process;
+import org.flowable.bpmn.model.*;
+import org.flowable.image.ProcessDiagramGenerator;
+
+import java.awt.*;
+import java.awt.image.BufferedImage;
+import java.io.InputStream;
+import java.util.List;
+import java.util.*;
+
+/**
+ * Class to generate an image based the diagram interchange information in a BPMN 2.0 process.
+ *
+ * @author Joram Barrez
+ * @author Tijs Rademakers
+ * @author Zheng Ji
+ */
+public class CustomDefaultProcessDiagramGenerator implements ProcessDiagramGenerator {
+
+ protected Map<Class<? extends BaseElement>, ActivityDrawInstruction> activityDrawInstructions = new HashMap<>();
+ protected Map<Class<? extends BaseElement>, ArtifactDrawInstruction> artifactDrawInstructions = new HashMap<>();
+
+ public CustomDefaultProcessDiagramGenerator() {
+ this(1.0);
+ }
+
+ // The instructions on how to draw a certain construct is
+ // created statically and stored in a map for performance.
+ public CustomDefaultProcessDiagramGenerator(final double scaleFactor) {
+ // start event
+ activityDrawInstructions.put(StartEvent.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ StartEvent startEvent = (StartEvent) flowNode;
+ if (startEvent.getEventDefinitions() != null && !startEvent.getEventDefinitions().isEmpty()) {
+ EventDefinition eventDefinition = startEvent.getEventDefinitions().get(0);
+ if (eventDefinition instanceof TimerEventDefinition) {
+ processDiagramCanvas.drawTimerStartEvent(graphicInfo, scaleFactor);
+ } else if (eventDefinition instanceof ErrorEventDefinition) {
+ processDiagramCanvas.drawErrorStartEvent(graphicInfo, scaleFactor);
+ } else if (eventDefinition instanceof EscalationEventDefinition) {
+ processDiagramCanvas.drawEscalationStartEvent(graphicInfo, scaleFactor);
+ } else if (eventDefinition instanceof ConditionalEventDefinition) {
+ processDiagramCanvas.drawConditionalStartEvent(graphicInfo, scaleFactor);
+ } else if (eventDefinition instanceof SignalEventDefinition) {
+ processDiagramCanvas.drawSignalStartEvent(graphicInfo, scaleFactor);
+ } else if (eventDefinition instanceof MessageEventDefinition) {
+ processDiagramCanvas.drawMessageStartEvent(graphicInfo, scaleFactor);
+ } else {
+ processDiagramCanvas.drawNoneStartEvent(graphicInfo);
+ }
+ } else {
+ List<ExtensionElement> eventTypeElements = startEvent.getExtensionElements().get("eventType");
+ if (eventTypeElements != null && eventTypeElements.size() > 0) {
+ processDiagramCanvas.drawEventRegistryStartEvent(graphicInfo, scaleFactor);
+
+ } else {
+ processDiagramCanvas.drawNoneStartEvent(graphicInfo);
+ }
+ }
+ }
+ });
+
+ // signal catch
+ activityDrawInstructions.put(IntermediateCatchEvent.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ IntermediateCatchEvent intermediateCatchEvent = (IntermediateCatchEvent) flowNode;
+ if (intermediateCatchEvent.getEventDefinitions() != null && !intermediateCatchEvent.getEventDefinitions().isEmpty()) {
+
+ if (intermediateCatchEvent.getEventDefinitions().get(0) instanceof SignalEventDefinition) {
+ processDiagramCanvas.drawCatchingSignalEvent(flowNode.getName(), graphicInfo, true, scaleFactor);
+ } else if (intermediateCatchEvent.getEventDefinitions().get(0) instanceof TimerEventDefinition) {
+ processDiagramCanvas.drawCatchingTimerEvent(flowNode.getName(), graphicInfo, true, scaleFactor);
+ } else if (intermediateCatchEvent.getEventDefinitions().get(0) instanceof MessageEventDefinition) {
+ processDiagramCanvas.drawCatchingMessageEvent(flowNode.getName(), graphicInfo, true, scaleFactor);
+ } else if (intermediateCatchEvent.getEventDefinitions().get(0) instanceof ConditionalEventDefinition) {
+ processDiagramCanvas.drawCatchingConditionalEvent(flowNode.getName(), graphicInfo, true, scaleFactor);
+ }
+ }
+ }
+ });
+
+ // signal throw
+ activityDrawInstructions.put(ThrowEvent.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ ThrowEvent throwEvent = (ThrowEvent) flowNode;
+ if (throwEvent.getEventDefinitions() != null && !throwEvent.getEventDefinitions().isEmpty()) {
+ if (throwEvent.getEventDefinitions().get(0) instanceof SignalEventDefinition) {
+ processDiagramCanvas.drawThrowingSignalEvent(graphicInfo, scaleFactor);
+ } else if (throwEvent.getEventDefinitions().get(0) instanceof EscalationEventDefinition) {
+ processDiagramCanvas.drawThrowingEscalationEvent(graphicInfo, scaleFactor);
+ } else if (throwEvent.getEventDefinitions().get(0) instanceof CompensateEventDefinition) {
+ processDiagramCanvas.drawThrowingCompensateEvent(graphicInfo, scaleFactor);
+ } else {
+ processDiagramCanvas.drawThrowingNoneEvent(graphicInfo, scaleFactor);
+ }
+ } else {
+ processDiagramCanvas.drawThrowingNoneEvent(graphicInfo, scaleFactor);
+ }
+ }
+ });
+
+ // end event
+ activityDrawInstructions.put(EndEvent.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ EndEvent endEvent = (EndEvent) flowNode;
+ if (endEvent.getEventDefinitions() != null && !endEvent.getEventDefinitions().isEmpty()) {
+ if (endEvent.getEventDefinitions().get(0) instanceof ErrorEventDefinition) {
+ processDiagramCanvas.drawErrorEndEvent(flowNode.getName(), graphicInfo, scaleFactor);
+ } else if (endEvent.getEventDefinitions().get(0) instanceof EscalationEventDefinition) {
+ processDiagramCanvas.drawEscalationEndEvent(flowNode.getName(), graphicInfo, scaleFactor);
+ } else {
+ processDiagramCanvas.drawNoneEndEvent(graphicInfo, scaleFactor);
+ }
+ } else {
+ processDiagramCanvas.drawNoneEndEvent(graphicInfo, scaleFactor);
+ }
+ }
+ });
+
+ // task
+ activityDrawInstructions.put(Task.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // user task
+ activityDrawInstructions.put(UserTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawUserTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // script task
+ activityDrawInstructions.put(ScriptTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawScriptTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // service task
+ activityDrawInstructions.put(ServiceTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ ServiceTask serviceTask = (ServiceTask) flowNode;
+ if ("camel".equalsIgnoreCase(serviceTask.getType())) {
+ processDiagramCanvas.drawCamelTask(serviceTask.getName(), graphicInfo, scaleFactor);
+ }else if (ServiceTask.HTTP_TASK.equalsIgnoreCase(serviceTask.getType())) {
+ processDiagramCanvas.drawHttpTask(serviceTask.getName(), graphicInfo, scaleFactor);
+ } else if (ServiceTask.DMN_TASK.equalsIgnoreCase(serviceTask.getType())) {
+ processDiagramCanvas.drawDMNTask(serviceTask.getName(), graphicInfo, scaleFactor);
+ } else if (ServiceTask.SHELL_TASK.equalsIgnoreCase(serviceTask.getType())) {
+ processDiagramCanvas.drawShellTask(serviceTask.getName(), graphicInfo, scaleFactor);
+ } else {
+ processDiagramCanvas.drawServiceTask(serviceTask.getName(), graphicInfo, scaleFactor);
+ }
+ }
+ });
+
+ // http service task
+ activityDrawInstructions.put(HttpServiceTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawHttpTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // receive task
+ activityDrawInstructions.put(ReceiveTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawReceiveTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // send task
+ activityDrawInstructions.put(SendTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawSendTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // manual task
+ activityDrawInstructions.put(ManualTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawManualTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // send event service task
+ activityDrawInstructions.put(SendEventServiceTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawSendEventServiceTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // external worker service task
+ activityDrawInstructions.put(ExternalWorkerServiceTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ ServiceTask serviceTask = (ServiceTask) flowNode;
+ processDiagramCanvas.drawServiceTask(serviceTask.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // case service task
+ activityDrawInstructions.put(CaseServiceTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawCaseServiceTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // businessRuleTask task
+ activityDrawInstructions.put(BusinessRuleTask.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawBusinessRuleTask(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // exclusive gateway
+ activityDrawInstructions.put(ExclusiveGateway.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawExclusiveGateway(graphicInfo, scaleFactor);
+ }
+ });
+
+ // inclusive gateway
+ activityDrawInstructions.put(InclusiveGateway.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawInclusiveGateway(graphicInfo, scaleFactor);
+ }
+ });
+
+ // parallel gateway
+ activityDrawInstructions.put(ParallelGateway.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawParallelGateway(graphicInfo, scaleFactor);
+ }
+ });
+
+ // event based gateway
+ activityDrawInstructions.put(EventGateway.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawEventBasedGateway(graphicInfo, scaleFactor);
+ }
+ });
+
+ // Boundary timer
+ activityDrawInstructions.put(BoundaryEvent.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ BoundaryEvent boundaryEvent = (BoundaryEvent) flowNode;
+ if (boundaryEvent.getEventDefinitions() != null && !boundaryEvent.getEventDefinitions().isEmpty()) {
+ EventDefinition eventDefinition = boundaryEvent.getEventDefinitions().get(0);
+ if (eventDefinition instanceof TimerEventDefinition) {
+ processDiagramCanvas.drawCatchingTimerEvent(flowNode.getName(), graphicInfo, boundaryEvent.isCancelActivity(), scaleFactor);
+
+ } else if (eventDefinition instanceof ConditionalEventDefinition) {
+ processDiagramCanvas.drawCatchingConditionalEvent(graphicInfo, boundaryEvent.isCancelActivity(), scaleFactor);
+
+ } else if (eventDefinition instanceof ErrorEventDefinition) {
+ processDiagramCanvas.drawCatchingErrorEvent(graphicInfo, boundaryEvent.isCancelActivity(), scaleFactor);
+
+ } else if (eventDefinition instanceof EscalationEventDefinition) {
+ processDiagramCanvas.drawCatchingEscalationEvent(graphicInfo, boundaryEvent.isCancelActivity(), scaleFactor);
+
+ } else if (eventDefinition instanceof SignalEventDefinition) {
+ processDiagramCanvas.drawCatchingSignalEvent(flowNode.getName(), graphicInfo, boundaryEvent.isCancelActivity(), scaleFactor);
+
+ } else if (eventDefinition instanceof MessageEventDefinition) {
+ processDiagramCanvas.drawCatchingMessageEvent(flowNode.getName(), graphicInfo, boundaryEvent.isCancelActivity(), scaleFactor);
+
+ } else if (eventDefinition instanceof CompensateEventDefinition) {
+ processDiagramCanvas.drawCatchingCompensateEvent(graphicInfo, boundaryEvent.isCancelActivity(), scaleFactor);
+ }
+
+ } else {
+ List<ExtensionElement> eventTypeElements = boundaryEvent.getExtensionElements().get("eventType");
+ if (eventTypeElements != null && eventTypeElements.size() > 0) {
+ processDiagramCanvas.drawCatchingEventRegistryEvent(flowNode.getName(), graphicInfo, boundaryEvent.isCancelActivity(), scaleFactor);
+ }
+ }
+ }
+ });
+
+ // subprocess
+ activityDrawInstructions.put(SubProcess.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ if (graphicInfo.getExpanded() != null && !graphicInfo.getExpanded()) {
+ processDiagramCanvas.drawCollapsedSubProcess(flowNode.getName(), graphicInfo, false, scaleFactor);
+ } else {
+ processDiagramCanvas.drawExpandedSubProcess(flowNode.getName(), graphicInfo, false, scaleFactor);
+ }
+ }
+ });
+
+ // transaction
+ activityDrawInstructions.put(Transaction.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ if (graphicInfo.getExpanded() != null && !graphicInfo.getExpanded()) {
+ processDiagramCanvas.drawCollapsedSubProcess(flowNode.getName(), graphicInfo, false, scaleFactor);
+ } else {
+ processDiagramCanvas.drawExpandedTransaction(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ }
+ });
+
+ // Event subprocess
+ activityDrawInstructions.put(EventSubProcess.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ if (graphicInfo.getExpanded() != null && !graphicInfo.getExpanded()) {
+ processDiagramCanvas.drawCollapsedSubProcess(flowNode.getName(), graphicInfo, true, scaleFactor);
+ } else {
+ processDiagramCanvas.drawExpandedSubProcess(flowNode.getName(), graphicInfo, true, scaleFactor);
+ }
+ }
+ });
+
+ // Adhoc subprocess
+ activityDrawInstructions.put(AdhocSubProcess.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ if (graphicInfo.getExpanded() != null && !graphicInfo.getExpanded()) {
+ processDiagramCanvas.drawCollapsedSubProcess(flowNode.getName(), graphicInfo, false, scaleFactor);
+ } else {
+ processDiagramCanvas.drawExpandedSubProcess(flowNode.getName(), graphicInfo, false, scaleFactor);
+ }
+ }
+ });
+
+ // call activity
+ activityDrawInstructions.put(CallActivity.class, new ActivityDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ processDiagramCanvas.drawCollapsedCallActivity(flowNode.getName(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // text annotation
+ artifactDrawInstructions.put(TextAnnotation.class, new ArtifactDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, Artifact artifact) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(artifact.getId());
+ TextAnnotation textAnnotation = (TextAnnotation) artifact;
+ processDiagramCanvas.drawTextAnnotation(textAnnotation.getText(), graphicInfo, scaleFactor);
+ }
+ });
+
+ // association
+ artifactDrawInstructions.put(Association.class, new ArtifactDrawInstruction() {
+
+ @Override
+ public void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, Artifact artifact) {
+ Association association = (Association) artifact;
+ String sourceRef = association.getSourceRef();
+ String targetRef = association.getTargetRef();
+
+ // source and target can be instance of FlowElement or Artifact
+ BaseElement sourceElement = bpmnModel.getFlowElement(sourceRef);
+ BaseElement targetElement = bpmnModel.getFlowElement(targetRef);
+ if (sourceElement == null) {
+ sourceElement = bpmnModel.getArtifact(sourceRef);
+ }
+ if (targetElement == null) {
+ targetElement = bpmnModel.getArtifact(targetRef);
+ }
+ List<GraphicInfo> graphicInfoList = bpmnModel.getFlowLocationGraphicInfo(artifact.getId());
+ graphicInfoList = connectionPerfectionizer(processDiagramCanvas, bpmnModel, sourceElement, targetElement, graphicInfoList);
+ int[] xPoints = new int[graphicInfoList.size()];
+ int[] yPoints = new int[graphicInfoList.size()];
+ for (int i = 1; i < graphicInfoList.size(); i++) {
+ GraphicInfo graphicInfo = graphicInfoList.get(i);
+ GraphicInfo previousGraphicInfo = graphicInfoList.get(i - 1);
+
+ if (i == 1) {
+ xPoints[0] = (int) previousGraphicInfo.getX();
+ yPoints[0] = (int) previousGraphicInfo.getY();
+ }
+ xPoints[i] = (int) graphicInfo.getX();
+ yPoints[i] = (int) graphicInfo.getY();
+ }
+
+ AssociationDirection associationDirection = association.getAssociationDirection();
+ processDiagramCanvas.drawAssociation(xPoints, yPoints, associationDirection, false, scaleFactor);
+ }
+ });
+ }
+
+ @Override
+ public InputStream generateDiagram(BpmnModel bpmnModel, String imageType, List<String> highLightedActivities, List<String> highLightedFlows,
+ String activityFontName, String labelFontName, String annotationFontName, ClassLoader customClassLoader, double scaleFactor, boolean drawSequenceFlowNameWithNoLabelDI) {
+
+ return generateProcessDiagram(bpmnModel, imageType, highLightedActivities, highLightedFlows,
+ activityFontName, labelFontName, annotationFontName, customClassLoader, scaleFactor, drawSequenceFlowNameWithNoLabelDI).generateImage(imageType);
+ }
+
+ @Override
+ public InputStream generateDiagram(BpmnModel bpmnModel, String imageType, List<String> highLightedActivities, List<String> highLightedFlows, boolean drawSequenceFlowNameWithNoLabelDI) {
+ return generateDiagram(bpmnModel, imageType, highLightedActivities, highLightedFlows, null, null, null, null, 1.0, drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ @Override
+ public InputStream generateDiagram(BpmnModel bpmnModel, String imageType,
+ List<String> highLightedActivities, List<String> highLightedFlows, double scaleFactor, boolean drawSequenceFlowNameWithNoLabelDI) {
+ return generateDiagram(bpmnModel, imageType, highLightedActivities, highLightedFlows, null, null, null, null, scaleFactor, drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ @Override
+ public InputStream generateDiagram(BpmnModel bpmnModel, String imageType, List<String> highLightedActivities, boolean drawSequenceFlowNameWithNoLabelDI) {
+ return generateDiagram(bpmnModel, imageType, highLightedActivities, Collections.emptyList(), drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ @Override
+ public InputStream generateDiagram(BpmnModel bpmnModel, String imageType, List<String> highLightedActivities, double scaleFactor, boolean drawSequenceFlowNameWithNoLabelDI) {
+ return generateDiagram(bpmnModel, imageType, highLightedActivities, Collections.emptyList(), scaleFactor, drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ @Override
+ public InputStream generateDiagram(BpmnModel bpmnModel, String imageType, String activityFontName,
+ String labelFontName, String annotationFontName, ClassLoader customClassLoader, boolean drawSequenceFlowNameWithNoLabelDI) {
+
+ return generateDiagram(bpmnModel, imageType, Collections.emptyList(), Collections.emptyList(),
+ activityFontName, labelFontName, annotationFontName, customClassLoader, 1.0, drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ @Override
+ public InputStream generateDiagram(BpmnModel bpmnModel, String imageType, String activityFontName,
+ String labelFontName, String annotationFontName, ClassLoader customClassLoader, double scaleFactor, boolean drawSequenceFlowNameWithNoLabelDI) {
+
+ return generateDiagram(bpmnModel, imageType, Collections.emptyList(), Collections.emptyList(),
+ activityFontName, labelFontName, annotationFontName, customClassLoader, scaleFactor, drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ @Override
+ public InputStream generatePngDiagram(BpmnModel bpmnModel, boolean drawSequenceFlowNameWithNoLabelDI) {
+ return generatePngDiagram(bpmnModel, 1.0, drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ @Override
+ public InputStream generatePngDiagram(BpmnModel bpmnModel, double scaleFactor, boolean drawSequenceFlowNameWithNoLabelDI) {
+ return generateDiagram(bpmnModel, "png", Collections.emptyList(), Collections.emptyList(), scaleFactor, drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ @Override
+ public InputStream generateJpgDiagram(BpmnModel bpmnModel) {
+ return generateJpgDiagram(bpmnModel, 1.0, false);
+ }
+
+ @Override
+ public InputStream generateJpgDiagram(BpmnModel bpmnModel, double scaleFactor, boolean drawSequenceFlowNameWithNoLabelDI) {
+ return generateDiagram(bpmnModel, "jpg", Collections.emptyList(), Collections.emptyList(), drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ public BufferedImage generateImage(BpmnModel bpmnModel, String imageType, List<String> highLightedActivities, List<String> highLightedFlows,
+ String activityFontName, String labelFontName, String annotationFontName, ClassLoader customClassLoader, double scaleFactor, boolean drawSequenceFlowNameWithNoLabelDI) {
+
+ return generateProcessDiagram(bpmnModel, imageType, highLightedActivities, highLightedFlows,
+ activityFontName, labelFontName, annotationFontName, customClassLoader, scaleFactor, drawSequenceFlowNameWithNoLabelDI).generateBufferedImage(imageType);
+ }
+
+ public BufferedImage generateImage(BpmnModel bpmnModel, String imageType,
+ List<String> highLightedActivities, List<String> highLightedFlows, double scaleFactor, boolean drawSequenceFlowNameWithNoLabelDI) {
+
+ return generateImage(bpmnModel, imageType, highLightedActivities, highLightedFlows, null, null, null, null, scaleFactor, drawSequenceFlowNameWithNoLabelDI);
+ }
+
+ @Override
+ public BufferedImage generatePngImage(BpmnModel bpmnModel, double scaleFactor) {
+ return generateImage(bpmnModel, "png", Collections.emptyList(), Collections.emptyList(), scaleFactor, false);
+ }
+
+ protected CustomDefaultProcessDiagramCanvas generateProcessDiagram(BpmnModel bpmnModel, String imageType,
+ List<String> highLightedActivities, List<String> highLightedFlows,
+ String activityFontName, String labelFontName, String annotationFontName, ClassLoader customClassLoader, double scaleFactor, boolean drawSequenceFlowNameWithNoLabelDI) {
+
+ prepareBpmnModel(bpmnModel);
+
+ CustomDefaultProcessDiagramCanvas processDiagramCanvas = initProcessDiagramCanvas(bpmnModel, imageType, activityFontName, labelFontName, annotationFontName, customClassLoader);
+
+ // Draw pool shape, if process is participant in collaboration
+ for (Pool pool : bpmnModel.getPools()) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(pool.getId());
+ processDiagramCanvas.drawPoolOrLane(pool.getName(), graphicInfo, scaleFactor);
+ }
+
+ // Draw lanes
+ for (Process process : bpmnModel.getProcesses()) {
+ for (Lane lane : process.getLanes()) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(lane.getId());
+ processDiagramCanvas.drawPoolOrLane(lane.getName(), graphicInfo, scaleFactor);
+ }
+ }
+
+ // Draw activities and their sequence-flows
+ for (Process process : bpmnModel.getProcesses()) {
+ for (FlowNode flowNode : process.findFlowElementsOfType(FlowNode.class)) {
+ if (!isPartOfCollapsedSubProcess(flowNode, bpmnModel)) {
+ drawActivity(processDiagramCanvas, bpmnModel, flowNode, highLightedActivities, highLightedFlows, scaleFactor, drawSequenceFlowNameWithNoLabelDI);
+ }
+ }
+ }
+
+ // Draw artifacts
+ for (Process process : bpmnModel.getProcesses()) {
+
+ for (Artifact artifact : process.getArtifacts()) {
+ drawArtifact(processDiagramCanvas, bpmnModel, artifact);
+ }
+
+ List<SubProcess> subProcesses = process.findFlowElementsOfType(SubProcess.class, true);
+ if (subProcesses != null) {
+ for (SubProcess subProcess : subProcesses) {
+
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(subProcess.getId());
+ if (graphicInfo != null && graphicInfo.getExpanded() != null && !graphicInfo.getExpanded()) {
+ continue;
+ }
+
+ if (!isPartOfCollapsedSubProcess(subProcess, bpmnModel)) {
+ for (Artifact subProcessArtifact : subProcess.getArtifacts()) {
+ drawArtifact(processDiagramCanvas, bpmnModel, subProcessArtifact);
+ }
+ }
+ }
+ }
+ }
+
+ return processDiagramCanvas;
+ }
+
+ protected void prepareBpmnModel(BpmnModel bpmnModel) {
+
+ // Need to make sure all elements have positive x and y.
+ // Check all graphicInfo and update the elements accordingly
+
+ List<GraphicInfo> allGraphicInfos = new ArrayList<>();
+ if (bpmnModel.getLocationMap() != null) {
+ allGraphicInfos.addAll(bpmnModel.getLocationMap().values());
+ }
+ if (bpmnModel.getLabelLocationMap() != null) {
+ allGraphicInfos.addAll(bpmnModel.getLabelLocationMap().values());
+ }
+ if (bpmnModel.getFlowLocationMap() != null) {
+ for (List<GraphicInfo> flowGraphicInfos : bpmnModel.getFlowLocationMap().values()) {
+ allGraphicInfos.addAll(flowGraphicInfos);
+ }
+ }
+
+ if (allGraphicInfos.size() > 0) {
+
+ boolean needsTranslationX = false;
+ boolean needsTranslationY = false;
+
+ double lowestX = 0.0;
+ double lowestY = 0.0;
+
+ // Collect lowest x and y
+ for (GraphicInfo graphicInfo : allGraphicInfos) {
+
+ double x = graphicInfo.getX();
+ double y = graphicInfo.getY();
+
+ if (x < lowestX) {
+ needsTranslationX = true;
+ lowestX = x;
+ }
+ if (y < lowestY) {
+ needsTranslationY = true;
+ lowestY = y;
+ }
+
+ }
+
+ // Update all graphicInfo objects
+ if (needsTranslationX || needsTranslationY) {
+
+ double translationX = Math.abs(lowestX);
+ double translationY = Math.abs(lowestY);
+
+ for (GraphicInfo graphicInfo : allGraphicInfos) {
+ if (needsTranslationX) {
+ graphicInfo.setX(graphicInfo.getX() + translationX);
+ }
+ if (needsTranslationY) {
+ graphicInfo.setY(graphicInfo.getY() + translationY);
+ }
+ }
+ }
+
+ }
+
+ }
+
+ protected void drawActivity(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel,
+ FlowNode flowNode, List<String> highLightedActivities, List<String> highLightedFlows, double scaleFactor, Boolean drawSequenceFlowNameWithNoLabelDI) {
+
+ ActivityDrawInstruction drawInstruction = activityDrawInstructions.get(flowNode.getClass());
+ if (drawInstruction != null) {
+
+ drawInstruction.draw(processDiagramCanvas, bpmnModel, flowNode);
+
+ // Gather info on the multi instance marker
+ boolean multiInstanceSequential = false;
+ boolean multiInstanceParallel = false;
+ boolean collapsed = false;
+ if (flowNode instanceof Activity) {
+ Activity activity = (Activity) flowNode;
+ MultiInstanceLoopCharacteristics multiInstanceLoopCharacteristics = activity.getLoopCharacteristics();
+ if (multiInstanceLoopCharacteristics != null) {
+ multiInstanceSequential = multiInstanceLoopCharacteristics.isSequential();
+ multiInstanceParallel = !multiInstanceSequential;
+ }
+ }
+
+ // Gather info on the collapsed marker
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+ if (flowNode instanceof SubProcess) {
+ collapsed = graphicInfo.getExpanded() != null && !graphicInfo.getExpanded();
+ } else if (flowNode instanceof CallActivity) {
+ collapsed = true;
+ }
+
+ if (scaleFactor == 1.0) {
+ // Actually draw the markers
+ processDiagramCanvas.drawActivityMarkers((int) graphicInfo.getX(), (int) graphicInfo.getY(), (int) graphicInfo.getWidth(), (int) graphicInfo.getHeight(),
+ multiInstanceSequential, multiInstanceParallel, collapsed);
+ }
+
+ // Draw highlighted activities
+ if (highLightedActivities.contains(flowNode.getId())) {
+ drawHighLightRed(processDiagramCanvas, bpmnModel.getGraphicInfo(flowNode.getId()));
+ } else if (highLightedActivities.contains(Color.RED.toString() + flowNode.getId())) {
+ drawHighLight(processDiagramCanvas, bpmnModel.getGraphicInfo(flowNode.getId()));
+ }
+
+ } else if (flowNode instanceof Task) {
+ activityDrawInstructions.get(Task.class).draw(processDiagramCanvas, bpmnModel, flowNode);
+
+ if (highLightedActivities.contains(flowNode.getId())) {
+ drawHighLightRed(processDiagramCanvas, bpmnModel.getGraphicInfo(flowNode.getId()));
+ } else if (highLightedActivities.contains(Color.RED.toString() + flowNode.getId())) {
+ drawHighLight(processDiagramCanvas, bpmnModel.getGraphicInfo(flowNode.getId()));
+ }
+ }
+
+ // Outgoing transitions of activity
+ for (SequenceFlow sequenceFlow : flowNode.getOutgoingFlows()) {
+ boolean highLighted = (highLightedFlows.contains(sequenceFlow.getId()));
+ String defaultFlow = null;
+ if (flowNode instanceof Activity) {
+ defaultFlow = ((Activity) flowNode).getDefaultFlow();
+ } else if (flowNode instanceof Gateway) {
+ defaultFlow = ((Gateway) flowNode).getDefaultFlow();
+ }
+
+ boolean isDefault = false;
+ if (defaultFlow != null && defaultFlow.equalsIgnoreCase(sequenceFlow.getId())) {
+ isDefault = true;
+ }
+ boolean drawConditionalIndicator = sequenceFlow.getConditionExpression() != null && sequenceFlow.getConditionExpression().trim().length() > 0 && !(flowNode instanceof Gateway);
+
+ String sourceRef = sequenceFlow.getSourceRef();
+ String targetRef = sequenceFlow.getTargetRef();
+ FlowElement sourceElement = bpmnModel.getFlowElement(sourceRef);
+ FlowElement targetElement = bpmnModel.getFlowElement(targetRef);
+ List<GraphicInfo> graphicInfoList = bpmnModel.getFlowLocationGraphicInfo(sequenceFlow.getId());
+ if (graphicInfoList != null && graphicInfoList.size() > 0) {
+ graphicInfoList = connectionPerfectionizer(processDiagramCanvas, bpmnModel, sourceElement, targetElement, graphicInfoList);
+ int[] xPoints = new int[graphicInfoList.size()];
+ int[] yPoints = new int[graphicInfoList.size()];
+
+ for (int i = 1; i < graphicInfoList.size(); i++) {
+ GraphicInfo graphicInfo = graphicInfoList.get(i);
+ GraphicInfo previousGraphicInfo = graphicInfoList.get(i - 1);
+
+ if (i == 1) {
+ xPoints[0] = (int) previousGraphicInfo.getX();
+ yPoints[0] = (int) previousGraphicInfo.getY();
+ }
+ xPoints[i] = (int) graphicInfo.getX();
+ yPoints[i] = (int) graphicInfo.getY();
+
+ }
+
+ processDiagramCanvas.drawSequenceflow(xPoints, yPoints, drawConditionalIndicator, isDefault, highLighted, scaleFactor);
+
+ // Draw sequenceflow label
+ GraphicInfo labelGraphicInfo = bpmnModel.getLabelGraphicInfo(sequenceFlow.getId());
+ if (labelGraphicInfo != null) {
+ processDiagramCanvas.drawLabel(sequenceFlow.getName(), labelGraphicInfo, false);
+ } else {
+ if (drawSequenceFlowNameWithNoLabelDI) {
+ GraphicInfo lineCenter = getLineCenter(graphicInfoList);
+ processDiagramCanvas.drawLabel(sequenceFlow.getName(), lineCenter, false);
+ }
+
+ }
+ }
+ }
+
+ // Nested elements
+ if (flowNode instanceof FlowElementsContainer) {
+ for (FlowElement nestedFlowElement : ((FlowElementsContainer) flowNode).getFlowElements()) {
+ if (nestedFlowElement instanceof FlowNode && !isPartOfCollapsedSubProcess(nestedFlowElement, bpmnModel)) {
+ drawActivity(processDiagramCanvas, bpmnModel, (FlowNode) nestedFlowElement,
+ highLightedActivities, highLightedFlows, scaleFactor, drawSequenceFlowNameWithNoLabelDI);
+ }
+ }
+ }
+ }
+
+ /**
+ * This method makes coordinates of connection flow better.
+ *
+ * @param processDiagramCanvas
+ * @param bpmnModel
+ * @param sourceElement
+ * @param targetElement
+ * @param graphicInfoList
+ * @return
+ */
+ protected static List<GraphicInfo> connectionPerfectionizer(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, BaseElement sourceElement, BaseElement targetElement, List<GraphicInfo> graphicInfoList) {
+ GraphicInfo sourceGraphicInfo = bpmnModel.getGraphicInfo(sourceElement.getId());
+ GraphicInfo targetGraphicInfo = bpmnModel.getGraphicInfo(targetElement.getId());
+
+ CustomDefaultProcessDiagramCanvas.SHAPE_TYPE sourceShapeType = getShapeType(sourceElement);
+ CustomDefaultProcessDiagramCanvas.SHAPE_TYPE targetShapeType = getShapeType(targetElement);
+
+ return processDiagramCanvas.connectionPerfectionizer(sourceShapeType, targetShapeType, sourceGraphicInfo, targetGraphicInfo, graphicInfoList);
+ }
+
+ /**
+ * This method returns shape type of base element.<br>
+ * Each element can be presented as rectangle, rhombus, or ellipse.
+ *
+ * @param baseElement
+ * @return CustomDefaultProcessDiagramCanvas.SHAPE_TYPE
+ */
+ protected static CustomDefaultProcessDiagramCanvas.SHAPE_TYPE getShapeType(BaseElement baseElement) {
+ if (baseElement instanceof Task || baseElement instanceof Activity || baseElement instanceof TextAnnotation) {
+ return CustomDefaultProcessDiagramCanvas.SHAPE_TYPE.Rectangle;
+ } else if (baseElement instanceof Gateway) {
+ return CustomDefaultProcessDiagramCanvas.SHAPE_TYPE.Rhombus;
+ } else if (baseElement instanceof Event) {
+ return CustomDefaultProcessDiagramCanvas.SHAPE_TYPE.Ellipse;
+ } else {
+ // unknown source element, just do not correct coordinates
+ }
+ return null;
+ }
+
+ protected static GraphicInfo getLineCenter(List<GraphicInfo> graphicInfoList) {
+ GraphicInfo gi = new GraphicInfo();
+
+ int[] xPoints = new int[graphicInfoList.size()];
+ int[] yPoints = new int[graphicInfoList.size()];
+
+ double length = 0;
+ double[] lengths = new double[graphicInfoList.size()];
+ lengths[0] = 0;
+ double m;
+ for (int i = 1; i < graphicInfoList.size(); i++) {
+ GraphicInfo graphicInfo = graphicInfoList.get(i);
+ GraphicInfo previousGraphicInfo = graphicInfoList.get(i - 1);
+
+ if (i == 1) {
+ xPoints[0] = (int) previousGraphicInfo.getX();
+ yPoints[0] = (int) previousGraphicInfo.getY();
+ }
+ xPoints[i] = (int) graphicInfo.getX();
+ yPoints[i] = (int) graphicInfo.getY();
+
+ length += Math.sqrt(
+ Math.pow((int) graphicInfo.getX() - (int) previousGraphicInfo.getX(), 2) +
+ Math.pow((int) graphicInfo.getY() - (int) previousGraphicInfo.getY(), 2));
+ lengths[i] = length;
+ }
+ m = length / 2;
+ int p1 = 0;
+ int p2 = 1;
+ for (int i = 1; i < lengths.length; i++) {
+ double len = lengths[i];
+ p1 = i - 1;
+ p2 = i;
+ if (len > m) {
+ break;
+ }
+ }
+
+ GraphicInfo graphicInfo1 = graphicInfoList.get(p1);
+ GraphicInfo graphicInfo2 = graphicInfoList.get(p2);
+
+ double AB = (int) graphicInfo2.getX() - (int) graphicInfo1.getX();
+ double OA = (int) graphicInfo2.getY() - (int) graphicInfo1.getY();
+ double OB = lengths[p2] - lengths[p1];
+ double ob = m - lengths[p1];
+ double ab = AB * ob / OB;
+ double oa = OA * ob / OB;
+
+ double mx = graphicInfo1.getX() + ab;
+ double my = graphicInfo1.getY() + oa;
+
+ gi.setX(mx);
+ gi.setY(my);
+ return gi;
+ }
+
+ protected void drawArtifact(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, Artifact artifact) {
+
+ ArtifactDrawInstruction drawInstruction = artifactDrawInstructions.get(artifact.getClass());
+ if (drawInstruction != null) {
+ drawInstruction.draw(processDiagramCanvas, bpmnModel, artifact);
+ }
+ }
+
+ private static void drawHighLight(CustomDefaultProcessDiagramCanvas processDiagramCanvas, GraphicInfo graphicInfo) {
+ processDiagramCanvas.drawHighLight((int) graphicInfo.getX(), (int) graphicInfo.getY(), (int) graphicInfo.getWidth(), (int) graphicInfo.getHeight());
+
+ }
+
+ private static void drawHighLightRed(CustomDefaultProcessDiagramCanvas processDiagramCanvas, GraphicInfo graphicInfo) {
+ processDiagramCanvas.drawHighLightRed((int) graphicInfo.getX(), (int) graphicInfo.getY(), (int) graphicInfo.getWidth(), (int) graphicInfo.getHeight());
+
+ }
+
+ protected static CustomDefaultProcessDiagramCanvas initProcessDiagramCanvas(BpmnModel bpmnModel, String imageType,
+ String activityFontName, String labelFontName, String annotationFontName, ClassLoader customClassLoader) {
+
+ // We need to calculate maximum values to know how big the image will be in its entirety
+ double minX = Double.MAX_VALUE;
+ double maxX = 0;
+ double minY = Double.MAX_VALUE;
+ double maxY = 0;
+
+ for (Pool pool : bpmnModel.getPools()) {
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(pool.getId());
+ minX = graphicInfo.getX();
+ maxX = graphicInfo.getX() + graphicInfo.getWidth();
+ minY = graphicInfo.getY();
+ maxY = graphicInfo.getY() + graphicInfo.getHeight();
+ }
+
+ List<FlowNode> flowNodes = gatherAllFlowNodes(bpmnModel);
+ for (FlowNode flowNode : flowNodes) {
+
+ GraphicInfo flowNodeGraphicInfo = bpmnModel.getGraphicInfo(flowNode.getId());
+
+ // width
+ if (flowNodeGraphicInfo.getX() + flowNodeGraphicInfo.getWidth() > maxX) {
+ maxX = flowNodeGraphicInfo.getX() + flowNodeGraphicInfo.getWidth();
+ }
+ if (flowNodeGraphicInfo.getX() < minX) {
+ minX = flowNodeGraphicInfo.getX();
+ }
+ // height
+ if (flowNodeGraphicInfo.getY() + flowNodeGraphicInfo.getHeight() > maxY) {
+ maxY = flowNodeGraphicInfo.getY() + flowNodeGraphicInfo.getHeight();
+ }
+ if (flowNodeGraphicInfo.getY() < minY) {
+ minY = flowNodeGraphicInfo.getY();
+ }
+
+ for (SequenceFlow sequenceFlow : flowNode.getOutgoingFlows()) {
+ List<GraphicInfo> graphicInfoList = bpmnModel.getFlowLocationGraphicInfo(sequenceFlow.getId());
+ if (graphicInfoList != null) {
+ for (GraphicInfo graphicInfo : graphicInfoList) {
+ // width
+ if (graphicInfo.getX() > maxX) {
+ maxX = graphicInfo.getX();
+ }
+ if (graphicInfo.getX() < minX) {
+ minX = graphicInfo.getX();
+ }
+ // height
+ if (graphicInfo.getY() > maxY) {
+ maxY = graphicInfo.getY();
+ }
+ if (graphicInfo.getY() < minY) {
+ minY = graphicInfo.getY();
+ }
+ }
+ }
+ }
+ }
+
+ List<Artifact> artifacts = gatherAllArtifacts(bpmnModel);
+ for (Artifact artifact : artifacts) {
+
+ GraphicInfo artifactGraphicInfo = bpmnModel.getGraphicInfo(artifact.getId());
+
+ if (artifactGraphicInfo != null) {
+ // width
+ if (artifactGraphicInfo.getX() + artifactGraphicInfo.getWidth() > maxX) {
+ maxX = artifactGraphicInfo.getX() + artifactGraphicInfo.getWidth();
+ }
+ if (artifactGraphicInfo.getX() < minX) {
+ minX = artifactGraphicInfo.getX();
+ }
+ // height
+ if (artifactGraphicInfo.getY() + artifactGraphicInfo.getHeight() > maxY) {
+ maxY = artifactGraphicInfo.getY() + artifactGraphicInfo.getHeight();
+ }
+ if (artifactGraphicInfo.getY() < minY) {
+ minY = artifactGraphicInfo.getY();
+ }
+ }
+
+ List<GraphicInfo> graphicInfoList = bpmnModel.getFlowLocationGraphicInfo(artifact.getId());
+ if (graphicInfoList != null) {
+ for (GraphicInfo graphicInfo : graphicInfoList) {
+ // width
+ if (graphicInfo.getX() > maxX) {
+ maxX = graphicInfo.getX();
+ }
+ if (graphicInfo.getX() < minX) {
+ minX = graphicInfo.getX();
+ }
+ // height
+ if (graphicInfo.getY() > maxY) {
+ maxY = graphicInfo.getY();
+ }
+ if (graphicInfo.getY() < minY) {
+ minY = graphicInfo.getY();
+ }
+ }
+ }
+ }
+
+ int nrOfLanes = 0;
+ for (Process process : bpmnModel.getProcesses()) {
+ for (Lane l : process.getLanes()) {
+
+ nrOfLanes++;
+
+ GraphicInfo graphicInfo = bpmnModel.getGraphicInfo(l.getId());
+ // // width
+ if (graphicInfo.getX() + graphicInfo.getWidth() > maxX) {
+ maxX = graphicInfo.getX() + graphicInfo.getWidth();
+ }
+ if (graphicInfo.getX() < minX) {
+ minX = graphicInfo.getX();
+ }
+ // height
+ if (graphicInfo.getY() + graphicInfo.getHeight() > maxY) {
+ maxY = graphicInfo.getY() + graphicInfo.getHeight();
+ }
+ if (graphicInfo.getY() < minY) {
+ minY = graphicInfo.getY();
+ }
+ }
+ }
+
+ // Special case, see https://activiti.atlassian.net/browse/ACT-1431
+ if (flowNodes.isEmpty() && bpmnModel.getPools().isEmpty() && nrOfLanes == 0) {
+ // Nothing to show
+ minX = 0;
+ minY = 0;
+ }
+
+ return new CustomDefaultProcessDiagramCanvas((int) maxX + 10, (int) maxY + 10, (int) minX, (int) minY,
+ imageType, activityFontName, labelFontName, annotationFontName, customClassLoader);
+ }
+
+ protected static List<Artifact> gatherAllArtifacts(BpmnModel bpmnModel) {
+ List<Artifact> artifacts = new ArrayList<>();
+ for (Process process : bpmnModel.getProcesses()) {
+ artifacts.addAll(process.getArtifacts());
+ }
+ return artifacts;
+ }
+
+ protected static List<FlowNode> gatherAllFlowNodes(BpmnModel bpmnModel) {
+ List<FlowNode> flowNodes = new ArrayList<>();
+ for (Process process : bpmnModel.getProcesses()) {
+ flowNodes.addAll(gatherAllFlowNodes(process));
+ }
+ return flowNodes;
+ }
+
+ protected static List<FlowNode> gatherAllFlowNodes(FlowElementsContainer flowElementsContainer) {
+ List<FlowNode> flowNodes = new ArrayList<>();
+ for (FlowElement flowElement : flowElementsContainer.getFlowElements()) {
+ if (flowElement instanceof FlowNode) {
+ flowNodes.add((FlowNode) flowElement);
+ }
+ if (flowElement instanceof FlowElementsContainer) {
+ flowNodes.addAll(gatherAllFlowNodes((FlowElementsContainer) flowElement));
+ }
+ }
+ return flowNodes;
+ }
+
+ protected boolean isPartOfCollapsedSubProcess(FlowElement flowElement, BpmnModel model) {
+ SubProcess subProcess = flowElement.getSubProcess();
+ if (subProcess != null) {
+ GraphicInfo graphicInfo = model.getGraphicInfo(subProcess.getId());
+ if (graphicInfo != null && graphicInfo.getExpanded() != null && !graphicInfo.getExpanded()) {
+ return true;
+ }
+
+ return isPartOfCollapsedSubProcess(subProcess, model);
+ }
+
+ return false;
+ }
+
+ public Map<Class<? extends BaseElement>, ActivityDrawInstruction> getActivityDrawInstructions() {
+ return activityDrawInstructions;
+ }
+
+ public void setActivityDrawInstructions(
+ Map<Class<? extends BaseElement>, ActivityDrawInstruction> activityDrawInstructions) {
+ this.activityDrawInstructions = activityDrawInstructions;
+ }
+
+ public Map<Class<? extends BaseElement>, ArtifactDrawInstruction> getArtifactDrawInstructions() {
+ return artifactDrawInstructions;
+ }
+
+ public void setArtifactDrawInstructions(
+ Map<Class<? extends BaseElement>, ArtifactDrawInstruction> artifactDrawInstructions) {
+ this.artifactDrawInstructions = artifactDrawInstructions;
+ }
+
+ protected interface ActivityDrawInstruction {
+ void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, FlowNode flowNode);
+ }
+
+ protected interface ArtifactDrawInstruction {
+ void draw(CustomDefaultProcessDiagramCanvas processDiagramCanvas, BpmnModel bpmnModel, Artifact artifact);
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/AddSequenceMultiInstanceCmd.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/AddSequenceMultiInstanceCmd.java
new file mode 100644
index 0000000..3cdfcf4
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/AddSequenceMultiInstanceCmd.java
@@ -0,0 +1,61 @@
+package org.dromara.workflow.flowable.cmd;
+
+import cn.hutool.core.collection.CollUtil;
+import org.flowable.common.engine.impl.interceptor.Command;
+import org.flowable.common.engine.impl.interceptor.CommandContext;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntity;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntityManager;
+import org.flowable.engine.impl.util.CommandContextUtil;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import static org.dromara.workflow.common.constant.FlowConstant.NUMBER_OF_INSTANCES;
+
+/**
+ * 涓茶鍔犵
+ *
+ * @author may
+ */
+public class AddSequenceMultiInstanceCmd implements Command<Void> {
+
+ /**
+ * 鎵цid
+ */
+ private final String executionId;
+
+ /**
+ * 浼氱浜哄憳闆嗗悎KEY
+ */
+ private final String assigneeList;
+
+ /**
+ * 鍔犵浜哄憳
+ */
+ private final List<Long> assignees;
+
+ public AddSequenceMultiInstanceCmd(String executionId, String assigneeList, List<Long> assignees) {
+ this.executionId = executionId;
+ this.assigneeList = assigneeList;
+ this.assignees = assignees;
+ }
+
+ @Override
+ public Void execute(CommandContext commandContext) {
+ ExecutionEntityManager executionEntityManager = CommandContextUtil.getExecutionEntityManager();
+ ExecutionEntity entity = executionEntityManager.findById(executionId);
+ // 澶氬疄渚嬩换鍔℃�绘暟鍔� assignees.size()
+ if (entity.getVariable(NUMBER_OF_INSTANCES) instanceof Integer nrOfInstances) {
+ entity.setVariable(NUMBER_OF_INSTANCES, nrOfInstances + assignees.size());
+ }
+ // 璁剧疆娴佺▼鍙橀噺
+ if (entity.getVariable(assigneeList) instanceof List<?> userIds) {
+ CollUtil.addAll(userIds, assignees);
+ Map<String, Object> variables = new HashMap<>(16);
+ variables.put(assigneeList, userIds);
+ entity.setVariables(variables);
+ }
+ return null;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/AttachmentCmd.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/AttachmentCmd.java
new file mode 100644
index 0000000..dd9849a
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/AttachmentCmd.java
@@ -0,0 +1,64 @@
+package org.dromara.workflow.flowable.cmd;
+
+import cn.hutool.core.collection.CollUtil;
+import org.dromara.common.core.domain.dto.OssDTO;
+import org.dromara.common.core.service.OssService;
+import org.dromara.common.core.utils.SpringUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.satoken.utils.LoginHelper;
+import org.flowable.common.engine.impl.interceptor.Command;
+import org.flowable.common.engine.impl.interceptor.CommandContext;
+import org.flowable.engine.impl.persistence.entity.AttachmentEntity;
+import org.flowable.engine.impl.persistence.entity.AttachmentEntityManager;
+import org.flowable.engine.impl.util.CommandContextUtil;
+
+import java.util.Date;
+import java.util.List;
+
+/**
+ * 闄勪欢涓婁紶
+ *
+ * @author may
+ */
+public class AttachmentCmd implements Command<Boolean> {
+
+ private final String fileId;
+
+ private final String taskId;
+
+ private final String processInstanceId;
+
+ public AttachmentCmd(String fileId, String taskId, String processInstanceId) {
+ this.fileId = fileId;
+ this.taskId = taskId;
+ this.processInstanceId = processInstanceId;
+ }
+
+ @Override
+ public Boolean execute(CommandContext commandContext) {
+ try {
+ if (StringUtils.isNotBlank(fileId)) {
+ List<OssDTO> ossList = SpringUtils.getBean(OssService.class).selectByIds(fileId);
+ if (CollUtil.isNotEmpty(ossList)) {
+ for (OssDTO oss : ossList) {
+ AttachmentEntityManager attachmentEntityManager = CommandContextUtil.getAttachmentEntityManager();
+ AttachmentEntity attachmentEntity = attachmentEntityManager.create();
+ attachmentEntity.setRevision(1);
+ attachmentEntity.setUserId(LoginHelper.getUserId().toString());
+ attachmentEntity.setName(oss.getOriginalName());
+ attachmentEntity.setDescription(oss.getOriginalName());
+ attachmentEntity.setType(oss.getFileSuffix());
+ attachmentEntity.setTaskId(taskId);
+ attachmentEntity.setProcessInstanceId(processInstanceId);
+ attachmentEntity.setContentId(oss.getOssId().toString());
+ attachmentEntity.setTime(new Date());
+ attachmentEntityManager.insert(attachmentEntity);
+ }
+ }
+ }
+ } catch (Exception e) {
+ throw new RuntimeException(e);
+ }
+ return true;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/DeleteExecutionCmd.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/DeleteExecutionCmd.java
new file mode 100644
index 0000000..215d310
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/DeleteExecutionCmd.java
@@ -0,0 +1,36 @@
+package org.dromara.workflow.flowable.cmd;
+
+import org.flowable.common.engine.impl.interceptor.Command;
+import org.flowable.common.engine.impl.interceptor.CommandContext;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntity;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntityManager;
+import org.flowable.engine.impl.util.CommandContextUtil;
+
+import java.io.Serializable;
+
+/**
+ * 鍒犻櫎鎵ц鏁版嵁
+ *
+ * @author may
+ */
+public class DeleteExecutionCmd implements Command<Void>, Serializable {
+
+ /**
+ * 鎵цid
+ */
+ private final String executionId;
+
+ public DeleteExecutionCmd(String executionId) {
+ this.executionId = executionId;
+ }
+
+ @Override
+ public Void execute(CommandContext commandContext) {
+ ExecutionEntityManager executionEntityManager = CommandContextUtil.getExecutionEntityManager();
+ ExecutionEntity entity = executionEntityManager.findById(executionId);
+ if (entity != null) {
+ executionEntityManager.deleteExecutionAndRelatedData(entity, "", false, false);
+ }
+ return null;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/DeleteSequenceMultiInstanceCmd.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/DeleteSequenceMultiInstanceCmd.java
new file mode 100644
index 0000000..6773eef
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/DeleteSequenceMultiInstanceCmd.java
@@ -0,0 +1,82 @@
+package org.dromara.workflow.flowable.cmd;
+
+import cn.hutool.core.util.ObjectUtil;
+import lombok.AllArgsConstructor;
+import org.flowable.common.engine.impl.interceptor.Command;
+import org.flowable.common.engine.impl.interceptor.CommandContext;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntity;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntityManager;
+import org.flowable.engine.impl.util.CommandContextUtil;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import static org.dromara.workflow.common.constant.FlowConstant.LOOP_COUNTER;
+import static org.dromara.workflow.common.constant.FlowConstant.NUMBER_OF_INSTANCES;
+
+
+/**
+ * 涓茶鍑忕
+ *
+ * @author may
+ */
+@AllArgsConstructor
+public class DeleteSequenceMultiInstanceCmd implements Command<Void> {
+
+ /**
+ * 褰撳墠鑺傜偣瀹℃壒浜哄憳id
+ */
+ private final String currentUserId;
+
+ /**
+ * 鎵цid
+ */
+ private final String executionId;
+
+ /**
+ * 浼氱浜哄憳闆嗗悎KEY
+ */
+ private final String assigneeList;
+
+ /**
+ * 鍑忕浜哄憳
+ */
+ private final List<Long> assignees;
+
+
+ @Override
+ @SuppressWarnings("unchecked")
+ public Void execute(CommandContext commandContext) {
+ ExecutionEntityManager executionEntityManager = CommandContextUtil.getExecutionEntityManager();
+ ExecutionEntity entity = executionEntityManager.findById(executionId);
+ // 璁剧疆娴佺▼鍙橀噺
+ List<Long> userIds = new ArrayList<>();
+ List<Object> variable = (List<Object>) entity.getVariable(assigneeList);
+ for (Object o : variable) {
+ userIds.add(Long.valueOf(o.toString()));
+ }
+ List<Long> userIdList = new ArrayList<>();
+ userIds.forEach(e -> {
+ Long userId = assignees.stream().filter(id -> ObjectUtil.equals(id, e)).findFirst().orElse(null);
+ if (userId == null) {
+ userIdList.add(e);
+ }
+ });
+ // 褰撳墠浠诲姟鎵ц浣嶇疆
+ int loopCounterIndex = -1;
+ for (int i = 0; i < userIdList.size(); i++) {
+ Long userId = userIdList.get(i);
+ if (currentUserId.equals(userId.toString())) {
+ loopCounterIndex = i;
+ }
+ }
+ Map<String, Object> variables = new HashMap<>(16);
+ variables.put(NUMBER_OF_INSTANCES, userIdList.size());
+ variables.put(assigneeList, userIdList);
+ variables.put(LOOP_COUNTER, loopCounterIndex);
+ entity.setVariables(variables);
+ return null;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/ExecutionChildByExecutionIdCmd.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/ExecutionChildByExecutionIdCmd.java
new file mode 100644
index 0000000..1f3088b
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/ExecutionChildByExecutionIdCmd.java
@@ -0,0 +1,39 @@
+package org.dromara.workflow.flowable.cmd;
+
+import org.dromara.common.core.utils.StreamUtils;
+import org.flowable.common.engine.impl.interceptor.Command;
+import org.flowable.common.engine.impl.interceptor.CommandContext;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntity;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntityManager;
+import org.flowable.engine.impl.util.CommandContextUtil;
+
+import java.io.Serializable;
+import java.util.List;
+
+/**
+ * 鑾峰彇骞惰缃戝叧鎵ц鍚庝繚鐣欑殑鎵ц瀹炰緥鏁版嵁
+ *
+ * @author may
+ */
+public class ExecutionChildByExecutionIdCmd implements Command<List<ExecutionEntity>>, Serializable {
+
+ /**
+ * 褰撳墠浠诲姟鎵ц瀹炰緥id
+ */
+ private final String executionId;
+
+ public ExecutionChildByExecutionIdCmd(String executionId) {
+ this.executionId = executionId;
+ }
+
+ @Override
+ public List<ExecutionEntity> execute(CommandContext commandContext) {
+ ExecutionEntityManager executionEntityManager = CommandContextUtil.getExecutionEntityManager();
+ // 鑾峰彇褰撳墠鎵ц鏁版嵁
+ ExecutionEntity executionEntity = executionEntityManager.findById(executionId);
+ // 閫氳繃褰撳墠鎵ц鏁版嵁鐨勭埗鎵ц锛屾煡璇㈡墍鏈夊瓙鎵ц鏁版嵁
+ List<ExecutionEntity> allChildrenExecution =
+ executionEntityManager.collectChildren(executionEntity.getParent());
+ return StreamUtils.filter(allChildrenExecution, e -> !e.isActive());
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/UpdateBusinessStatusCmd.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/UpdateBusinessStatusCmd.java
new file mode 100644
index 0000000..3ba120a
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/UpdateBusinessStatusCmd.java
@@ -0,0 +1,37 @@
+package org.dromara.workflow.flowable.cmd;
+
+import org.dromara.common.core.exception.ServiceException;
+import org.flowable.common.engine.impl.interceptor.Command;
+import org.flowable.common.engine.impl.interceptor.CommandContext;
+import org.flowable.engine.impl.persistence.entity.HistoricProcessInstanceEntity;
+import org.flowable.engine.impl.persistence.entity.HistoricProcessInstanceEntityManager;
+import org.flowable.engine.impl.util.CommandContextUtil;
+
+/**
+ * 淇敼娴佺▼鐘舵��
+ *
+ * @author may
+ */
+public class UpdateBusinessStatusCmd implements Command<Boolean> {
+
+ private final String processInstanceId;
+ private final String status;
+
+ public UpdateBusinessStatusCmd(String processInstanceId, String status) {
+ this.processInstanceId = processInstanceId;
+ this.status = status;
+ }
+
+ @Override
+ public Boolean execute(CommandContext commandContext) {
+ try {
+ HistoricProcessInstanceEntityManager manager = CommandContextUtil.getHistoricProcessInstanceEntityManager();
+ HistoricProcessInstanceEntity processInstance = manager.findById(processInstanceId);
+ processInstance.setBusinessStatus(status);
+ manager.update(processInstance);
+ return true;
+ } catch (Exception e) {
+ throw new ServiceException(e.getMessage());
+ }
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/UpdateHiTaskInstCmd.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/UpdateHiTaskInstCmd.java
new file mode 100644
index 0000000..42f6d1c
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/cmd/UpdateHiTaskInstCmd.java
@@ -0,0 +1,51 @@
+package org.dromara.workflow.flowable.cmd;
+
+import org.dromara.common.core.exception.ServiceException;
+import org.flowable.common.engine.impl.interceptor.Command;
+import org.flowable.common.engine.impl.interceptor.CommandContext;
+import org.flowable.engine.impl.util.CommandContextUtil;
+import org.flowable.task.service.HistoricTaskService;
+import org.flowable.task.service.impl.persistence.entity.HistoricTaskInstanceEntity;
+
+import java.util.Date;
+import java.util.List;
+
+
+/**
+ * 淇敼娴佺▼鍘嗗彶
+ *
+ * @author may
+ */
+public class UpdateHiTaskInstCmd implements Command<Boolean> {
+
+ private final List<String> taskIds;
+
+ private final String processDefinitionId;
+
+ private final String processInstanceId;
+
+ public UpdateHiTaskInstCmd(List<String> taskIds, String processDefinitionId, String processInstanceId) {
+ this.taskIds = taskIds;
+ this.processDefinitionId = processDefinitionId;
+ this.processInstanceId = processInstanceId;
+ }
+
+ @Override
+ public Boolean execute(CommandContext commandContext) {
+ try {
+ HistoricTaskService historicTaskService = CommandContextUtil.getHistoricTaskService();
+ for (String taskId : taskIds) {
+ HistoricTaskInstanceEntity historicTask = historicTaskService.getHistoricTask(taskId);
+ if (historicTask != null) {
+ historicTask.setProcessDefinitionId(processDefinitionId);
+ historicTask.setProcessInstanceId(processInstanceId);
+ historicTask.setCreateTime(new Date());
+ CommandContextUtil.getHistoricTaskService().updateHistoricTask(historicTask, true);
+ }
+ }
+ return true;
+ } catch (Exception e) {
+ throw new ServiceException(e.getMessage());
+ }
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/config/FlowableConfig.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/config/FlowableConfig.java
new file mode 100644
index 0000000..1494bf3
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/config/FlowableConfig.java
@@ -0,0 +1,32 @@
+package org.dromara.workflow.flowable.config;
+
+import com.baomidou.mybatisplus.core.incrementer.IdentifierGenerator;
+import org.dromara.workflow.flowable.handler.TaskTimeoutJobHandler;
+import org.flowable.spring.SpringProcessEngineConfiguration;
+import org.flowable.spring.boot.EngineConfigurationConfigurer;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.context.annotation.Configuration;
+
+import java.util.Collections;
+
+
+/**
+ * flowable閰嶇疆
+ *
+ * @author may
+ */
+@Configuration
+public class FlowableConfig implements EngineConfigurationConfigurer<SpringProcessEngineConfiguration> {
+
+ @Autowired
+ private GlobalFlowableListener globalFlowableListener;
+ @Autowired
+ private IdentifierGenerator identifierGenerator;
+
+ @Override
+ public void configure(SpringProcessEngineConfiguration processEngineConfiguration) {
+ processEngineConfiguration.setIdGenerator(() -> identifierGenerator.nextId(null).toString());
+ processEngineConfiguration.setEventListeners(Collections.singletonList(globalFlowableListener));
+ processEngineConfiguration.addCustomJobHandler(new TaskTimeoutJobHandler());
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/config/GlobalFlowableListener.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/config/GlobalFlowableListener.java
new file mode 100644
index 0000000..9bb971a
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/config/GlobalFlowableListener.java
@@ -0,0 +1,139 @@
+package org.dromara.workflow.flowable.config;
+
+import cn.hutool.core.collection.CollUtil;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.tenant.helper.TenantHelper;
+import org.dromara.workflow.common.enums.TaskStatusEnum;
+import org.dromara.workflow.flowable.handler.TaskTimeoutJobHandler;
+import org.dromara.workflow.utils.QueryUtils;
+import org.flowable.bpmn.model.BoundaryEvent;
+import org.flowable.bpmn.model.BpmnModel;
+import org.flowable.bpmn.model.FlowElement;
+import org.flowable.common.engine.api.delegate.event.*;
+import org.flowable.common.engine.impl.cfg.TransactionState;
+import org.flowable.engine.RepositoryService;
+import org.flowable.engine.RuntimeService;
+import org.flowable.engine.TaskService;
+import org.flowable.engine.impl.util.CommandContextUtil;
+import org.flowable.engine.runtime.Execution;
+import org.flowable.engine.task.Comment;
+import org.flowable.job.service.TimerJobService;
+import org.flowable.job.service.impl.persistence.entity.JobEntity;
+import org.flowable.job.service.impl.persistence.entity.TimerJobEntity;
+import org.flowable.task.api.Task;
+import org.flowable.task.service.impl.persistence.entity.TaskEntity;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.context.annotation.Lazy;
+import org.springframework.stereotype.Component;
+
+import java.util.Date;
+import java.util.List;
+
+
+/**
+ * 寮曟搸璋冨害鐩戝惉
+ *
+ * @author may
+ */
+@Component
+public class GlobalFlowableListener implements FlowableEventListener {
+
+ @Autowired
+ @Lazy
+ private TaskService taskService;
+
+ @Autowired
+ @Lazy
+ private RuntimeService runtimeService;
+
+ @Autowired
+ @Lazy
+ private RepositoryService repositoryService;
+
+ @Value("${flowable.async-executor-activate}")
+ private boolean asyncExecutorActivate;
+
+ @Override
+ public void onEvent(FlowableEvent flowableEvent) {
+ if (flowableEvent instanceof FlowableEngineEvent flowableEngineEvent) {
+ FlowableEngineEventType engineEventType = (FlowableEngineEventType) flowableEvent.getType();
+ switch (engineEventType) {
+ case JOB_EXECUTION_SUCCESS -> jobExecutionSuccess((FlowableEngineEntityEvent) flowableEngineEvent);
+ case TASK_DUEDATE_CHANGED, TASK_CREATED -> {
+ FlowableEntityEvent flowableEntityEvent = (FlowableEntityEvent) flowableEngineEvent;
+ Object entityObject = flowableEntityEvent.getEntity();
+ TaskEntity task = (TaskEntity) entityObject;
+ if (asyncExecutorActivate && task.getDueDate() != null && task.getDueDate().after(new Date())) {
+ //鍒犻櫎涔嬪墠宸茬粡瀛樺湪鐨勫畾鏃朵换鍔�
+ TimerJobService timerJobService = CommandContextUtil.getTimerJobService();
+ List<TimerJobEntity> timerJobEntityList = timerJobService.findTimerJobsByProcessInstanceId(task.getProcessInstanceId());
+ if (!CollUtil.isEmpty(timerJobEntityList)) {
+ for (TimerJobEntity timerJobEntity : timerJobEntityList) {
+ String taskId = timerJobEntity.getJobHandlerConfiguration();
+ if (task.getId().equals(taskId)) {
+ timerJobService.deleteTimerJob(timerJobEntity);
+ }
+ }
+ }
+ //鍒涘缓job瀵硅薄
+ TimerJobEntity timer = timerJobService.createTimerJob();
+ timer.setTenantId(TenantHelper.getTenantId());
+ //璁剧疆job绫诲瀷
+ timer.setJobType(JobEntity.JOB_TYPE_TIMER);
+ timer.setJobHandlerType(TaskTimeoutJobHandler.TYPE);
+ timer.setDuedate(task.getDueDate());
+ timer.setProcessInstanceId(task.getProcessInstanceId());
+ //璁剧疆浠诲姟id
+ timer.setJobHandlerConfiguration(task.getId());
+ //淇濆瓨骞惰Е鍙戜簨浠�
+ timerJobService.scheduleTimerJob(timer);
+ }
+ }
+ }
+ }
+ }
+
+ @Override
+ public boolean isFailOnException() {
+ return true;
+ }
+
+ @Override
+ public boolean isFireOnTransactionLifecycleEvent() {
+ return false;
+ }
+
+ @Override
+ public String getOnTransaction() {
+ return TransactionState.COMMITTED.name();
+ }
+
+ /**
+ * 澶勭悊杈圭晫瀹氭椂浜嬩欢鑷姩瀹℃壒璁板綍
+ *
+ * @param event 浜嬩欢
+ */
+ protected void jobExecutionSuccess(FlowableEngineEntityEvent event) {
+ if (event != null && StringUtils.isNotBlank(event.getExecutionId())) {
+ Execution execution = runtimeService.createExecutionQuery().executionId(event.getExecutionId()).singleResult();
+ if (execution != null) {
+ BpmnModel bpmnModel = repositoryService.getBpmnModel(event.getProcessDefinitionId());
+ FlowElement flowElement = bpmnModel.getFlowElement(execution.getActivityId());
+ if (flowElement instanceof BoundaryEvent) {
+ String attachedToRefId = ((BoundaryEvent) flowElement).getAttachedToRefId();
+ List<Execution> list = runtimeService.createExecutionQuery().activityId(attachedToRefId).list();
+ for (Execution ex : list) {
+ Task task = QueryUtils.taskQuery().executionId(ex.getId()).singleResult();
+ if (task != null) {
+ List<Comment> taskComments = taskService.getTaskComments(task.getId());
+ if (CollUtil.isEmpty(taskComments)) {
+ taskService.addComment(task.getId(), task.getProcessInstanceId(), TaskStatusEnum.PASS.getStatus(), "瓒呮椂鑷姩瀹℃壒!");
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/handler/TaskTimeoutJobHandler.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/handler/TaskTimeoutJobHandler.java
new file mode 100644
index 0000000..7685423
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/handler/TaskTimeoutJobHandler.java
@@ -0,0 +1,38 @@
+package org.dromara.workflow.flowable.handler;
+
+import org.dromara.workflow.common.enums.TaskStatusEnum;
+import org.flowable.common.engine.impl.interceptor.CommandContext;
+import org.flowable.engine.TaskService;
+import org.flowable.engine.impl.jobexecutor.TimerEventHandler;
+import org.flowable.engine.impl.util.CommandContextUtil;
+import org.flowable.job.service.JobHandler;
+import org.flowable.job.service.impl.persistence.entity.JobEntity;
+import org.flowable.task.api.Task;
+import org.flowable.task.api.TaskQuery;
+import org.flowable.variable.api.delegate.VariableScope;
+
+/**
+ * 鍔炵悊瓒呮椂(杩囨湡)浠诲姟
+ *
+ * @author may
+ */
+public class TaskTimeoutJobHandler extends TimerEventHandler implements JobHandler {
+
+ public static final String TYPE = "taskTimeout";
+
+ @Override
+ public String getType() {
+ return TYPE;
+ }
+
+ @Override
+ public void execute(JobEntity job, String configuration, VariableScope variableScope, CommandContext commandContext) {
+ TaskService taskService = CommandContextUtil.getProcessEngineConfiguration(commandContext)
+ .getTaskService();
+ Task task = taskService.createTaskQuery().taskId(configuration).singleResult();
+ if (task != null) {
+ taskService.addComment(task.getId(), task.getProcessInstanceId(), TaskStatusEnum.TIMEOUT.getStatus(), "瓒呮椂鑷姩瀹℃壒!");
+ taskService.complete(configuration);
+ }
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowEventStrategy.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowEventStrategy.java
new file mode 100644
index 0000000..9da5776
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowEventStrategy.java
@@ -0,0 +1,73 @@
+package org.dromara.workflow.flowable.strategy;
+
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.workflow.annotation.FlowListenerAnnotation;
+import org.springframework.beans.BeansException;
+import org.springframework.beans.factory.config.BeanPostProcessor;
+import org.springframework.stereotype.Component;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * 娴佺▼浠诲姟鐩戝惉绛栫暐
+ *
+ * @author may
+ * @date 2023-12-27
+ */
+@Component
+public class FlowEventStrategy implements BeanPostProcessor {
+
+ private final Map<String, FlowTaskEventHandler> flowTaskEventHandlers = new HashMap<>();
+ private final Map<String, FlowProcessEventHandler> flowProcessEventHandlers = new HashMap<>();
+
+ @Override
+ public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
+ if (bean instanceof FlowTaskEventHandler) {
+ FlowListenerAnnotation annotation = bean.getClass().getAnnotation(FlowListenerAnnotation.class);
+ if (null != annotation) {
+ if (StringUtils.isNotBlank(annotation.processDefinitionKey()) && StringUtils.isNotBlank(annotation.taskDefId())) {
+ String id = annotation.processDefinitionKey() + "_" + annotation.taskDefId();
+ if (!flowTaskEventHandlers.containsKey(id)) {
+ flowTaskEventHandlers.put(id, (FlowTaskEventHandler) bean);
+ }
+ }
+ }
+ }
+ if (bean instanceof FlowProcessEventHandler) {
+ FlowListenerAnnotation annotation = bean.getClass().getAnnotation(FlowListenerAnnotation.class);
+ if (null != annotation) {
+ if (StringUtils.isNotBlank(annotation.processDefinitionKey()) && StringUtils.isBlank(annotation.taskDefId())) {
+ if (!flowProcessEventHandlers.containsKey(annotation.processDefinitionKey())) {
+ flowProcessEventHandlers.put(annotation.processDefinitionKey(), (FlowProcessEventHandler) bean);
+ }
+ }
+ }
+ }
+ return BeanPostProcessor.super.postProcessBeforeInitialization(bean, beanName);
+ }
+
+ /**
+ * 鑾峰彇鍙墽琛宐ean
+ *
+ * @param key key
+ */
+ public FlowTaskEventHandler getTaskHandler(String key) {
+ if (!flowTaskEventHandlers.containsKey(key)) {
+ return null;
+ }
+ return flowTaskEventHandlers.get(key);
+ }
+
+ /**
+ * 鑾峰彇鍙墽琛宐ean
+ *
+ * @param key key
+ */
+ public FlowProcessEventHandler getProcessHandler(String key) {
+ if (!flowProcessEventHandlers.containsKey(key)) {
+ return null;
+ }
+ return flowProcessEventHandlers.get(key);
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowProcessEventHandler.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowProcessEventHandler.java
new file mode 100644
index 0000000..4af2c47
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowProcessEventHandler.java
@@ -0,0 +1,20 @@
+package org.dromara.workflow.flowable.strategy;
+
+
+/**
+ * 娴佺▼鐩戝惉
+ *
+ * @author may
+ * @date 2023-12-27
+ */
+public interface FlowProcessEventHandler {
+
+ /**
+ * 鎵ц鍔炵悊浠诲姟鐩戝惉
+ *
+ * @param businessKey 涓氬姟id
+ * @param status 鐘舵��
+ * @param submit 褰撲负true鏃朵负鐢宠浜鸿妭鐐瑰姙鐞�
+ */
+ void handleProcess(String businessKey, String status, boolean submit);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowTaskEventHandler.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowTaskEventHandler.java
new file mode 100644
index 0000000..b338900
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/flowable/strategy/FlowTaskEventHandler.java
@@ -0,0 +1,19 @@
+package org.dromara.workflow.flowable.strategy;
+
+
+/**
+ * 娴佺▼浠诲姟鐩戝惉
+ *
+ * @author may
+ * @date 2023-12-27
+ */
+public interface FlowTaskEventHandler {
+
+ /**
+ * 鎵ц鍔炵悊浠诲姟鐩戝惉
+ *
+ * @param taskId 浠诲姟ID
+ * @param businessKey 涓氬姟id
+ */
+ void handleTask(String taskId, String businessKey);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestCustomProcessHandler.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestCustomProcessHandler.java
new file mode 100644
index 0000000..29886d8
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestCustomProcessHandler.java
@@ -0,0 +1,31 @@
+package org.dromara.workflow.listener;
+
+import lombok.extern.slf4j.Slf4j;
+import org.dromara.workflow.annotation.FlowListenerAnnotation;
+import org.dromara.workflow.flowable.strategy.FlowProcessEventHandler;
+import org.springframework.stereotype.Component;
+
+/**
+ * 鑷畾涔夌洃鍚祴璇�
+ *
+ * @author may
+ * @date 2023-12-27
+ */
+@Slf4j
+@Component
+@FlowListenerAnnotation(processDefinitionKey = "leave1")
+public class TestCustomProcessHandler implements FlowProcessEventHandler {
+
+
+ /**
+ * 鎵ц鍔炵悊浠诲姟鐩戝惉
+ *
+ * @param businessKey 涓氬姟id
+ * @param status 鐘舵��
+ * @param submit 褰撲负true鏃朵负鐢宠浜鸿妭鐐瑰姙鐞�
+ */
+ @Override
+ public void handleProcess(String businessKey, String status, boolean submit) {
+ log.info("涓氬姟ID:" + businessKey + ",鐘舵��:" + status);
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestCustomTaskHandler.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestCustomTaskHandler.java
new file mode 100644
index 0000000..d85286d
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestCustomTaskHandler.java
@@ -0,0 +1,23 @@
+package org.dromara.workflow.listener;
+
+import lombok.extern.slf4j.Slf4j;
+import org.dromara.workflow.annotation.FlowListenerAnnotation;
+import org.dromara.workflow.flowable.strategy.FlowTaskEventHandler;
+import org.springframework.stereotype.Component;
+
+/**
+ * 鑷畾涔夌洃鍚祴璇�
+ *
+ * @author may
+ * @date 2023-12-27
+ */
+@Slf4j
+@Component
+@FlowListenerAnnotation(processDefinitionKey = "leave1", taskDefId = "Activity_14633hx")
+public class TestCustomTaskHandler implements FlowTaskEventHandler {
+
+ @Override
+ public void handleTask(String taskId, String businessKey) {
+ log.info("浠诲姟ID:" + taskId + ",涓氬姟ID:" + businessKey);
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestLeaveExecutionListener.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestLeaveExecutionListener.java
new file mode 100644
index 0000000..11f844e
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestLeaveExecutionListener.java
@@ -0,0 +1,28 @@
+package org.dromara.workflow.listener;
+
+import lombok.RequiredArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
+import org.dromara.workflow.utils.QueryUtils;
+import org.flowable.engine.TaskService;
+import org.flowable.engine.delegate.DelegateExecution;
+import org.flowable.engine.delegate.ExecutionListener;
+import org.flowable.task.api.Task;
+import org.springframework.stereotype.Component;
+
+/**
+ * 娴佺▼瀹炰緥鐩戝惉娴嬭瘯
+ *
+ * @author may
+ * @date 2023-12-12
+ */
+@Slf4j
+@RequiredArgsConstructor
+@Component("testLeaveExecutionListener")
+public class TestLeaveExecutionListener implements ExecutionListener {
+
+ @Override
+ public void notify(DelegateExecution execution) {
+ Task task = QueryUtils.taskQuery().executionId(execution.getId()).singleResult();
+ log.info("鎵ц鐩戝惉銆�" + task.getName() + "銆�");
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestLeaveTaskListener.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestLeaveTaskListener.java
new file mode 100644
index 0000000..5c62417
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/listener/TestLeaveTaskListener.java
@@ -0,0 +1,21 @@
+package org.dromara.workflow.listener;
+
+import lombok.extern.slf4j.Slf4j;
+import org.flowable.task.service.delegate.DelegateTask;
+import org.flowable.task.service.delegate.TaskListener;
+import org.springframework.stereotype.Component;
+
+/**
+ * 娴佺▼浠诲姟鐩戝惉娴嬭瘯
+ *
+ * @author may
+ * @date 2023-12-12
+ */
+@Slf4j
+@Component("testLeaveTaskListener")
+public class TestLeaveTaskListener implements TaskListener {
+ @Override
+ public void notify(DelegateTask delegateTask) {
+ log.info("鎵ц鐩戝惉銆�" + delegateTask.getName() + "銆�");
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActHiProcinstMapper.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActHiProcinstMapper.java
new file mode 100644
index 0000000..a3a41c9
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActHiProcinstMapper.java
@@ -0,0 +1,16 @@
+package org.dromara.workflow.mapper;
+
+import com.baomidou.mybatisplus.annotation.InterceptorIgnore;
+import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
+import org.dromara.workflow.domain.ActHiProcinst;
+
+/**
+ * 娴佺▼瀹炰緥Mapper鎺ュ彛
+ *
+ * @author may
+ * @date 2023-07-22
+ */
+@InterceptorIgnore(tenantLine = "true")
+public interface ActHiProcinstMapper extends BaseMapperPlus<ActHiProcinst, ActHiProcinst> {
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActHiTaskinstMapper.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActHiTaskinstMapper.java
new file mode 100644
index 0000000..63b394b
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActHiTaskinstMapper.java
@@ -0,0 +1,16 @@
+package org.dromara.workflow.mapper;
+
+import com.baomidou.mybatisplus.annotation.InterceptorIgnore;
+import org.dromara.workflow.domain.ActHiTaskinst;
+import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
+
+/**
+ * 娴佺▼鍘嗗彶浠诲姟Mapper鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-02
+ */
+@InterceptorIgnore(tenantLine = "true")
+public interface ActHiTaskinstMapper extends BaseMapperPlus<ActHiTaskinst, ActHiTaskinst> {
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActTaskMapper.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActTaskMapper.java
new file mode 100644
index 0000000..63c5ecb
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/ActTaskMapper.java
@@ -0,0 +1,47 @@
+package org.dromara.workflow.mapper;
+
+import com.baomidou.mybatisplus.annotation.InterceptorIgnore;
+import com.baomidou.mybatisplus.core.conditions.Wrapper;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.core.toolkit.Constants;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import org.apache.ibatis.annotations.Param;
+import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
+import org.dromara.workflow.domain.vo.TaskVo;
+
+
+/**
+ * 浠诲姟淇℃伅Mapper鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-02
+ */
+@InterceptorIgnore(tenantLine = "true")
+public interface ActTaskMapper extends BaseMapperPlus<TaskVo, TaskVo> {
+ /**
+ * 鑾峰彇寰呭姙淇℃伅
+ *
+ * @param page 鍒嗛〉
+ * @param queryWrapper 鏉′欢
+ * @return 缁撴灉
+ */
+ Page<TaskVo> getTaskWaitByPage(@Param("page") Page<TaskVo> page, @Param(Constants.WRAPPER) Wrapper<TaskVo> queryWrapper);
+
+ /**
+ * 鑾峰彇宸插姙
+ *
+ * @param page 鍒嗛〉
+ * @param queryWrapper 鏉′欢
+ * @return 缁撴灉
+ */
+ Page<TaskVo> getTaskFinishByPage(@Param("page") Page<TaskVo> page, @Param(Constants.WRAPPER) Wrapper<TaskVo> queryWrapper);
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勬妱閫�
+ *
+ * @param page 鍒嗛〉
+ * @param queryWrapper 鏉′欢
+ * @return 缁撴灉
+ */
+ Page<TaskVo> getTaskCopyByPage(@Param("page") Page<TaskVo> page, @Param(Constants.WRAPPER) QueryWrapper<TaskVo> queryWrapper);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/TestLeaveMapper.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/TestLeaveMapper.java
new file mode 100644
index 0000000..cd1edba
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/TestLeaveMapper.java
@@ -0,0 +1,15 @@
+package org.dromara.workflow.mapper;
+
+import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
+import org.dromara.workflow.domain.TestLeave;
+import org.dromara.workflow.domain.vo.TestLeaveVo;
+
+/**
+ * 璇峰亣Mapper鎺ュ彛
+ *
+ * @author may
+ * @date 2023-07-21
+ */
+public interface TestLeaveMapper extends BaseMapperPlus<TestLeave, TestLeaveVo> {
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfCategoryMapper.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfCategoryMapper.java
new file mode 100644
index 0000000..98aea02
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfCategoryMapper.java
@@ -0,0 +1,15 @@
+package org.dromara.workflow.mapper;
+
+import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
+import org.dromara.workflow.domain.WfCategory;
+import org.dromara.workflow.domain.vo.WfCategoryVo;
+
+/**
+ * 娴佺▼鍒嗙被Mapper鎺ュ彛
+ *
+ * @author may
+ * @date 2023-06-27
+ */
+public interface WfCategoryMapper extends BaseMapperPlus<WfCategory, WfCategoryVo> {
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfDefinitionConfigMapper.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfDefinitionConfigMapper.java
new file mode 100644
index 0000000..ee20882
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfDefinitionConfigMapper.java
@@ -0,0 +1,15 @@
+package org.dromara.workflow.mapper;
+
+import org.dromara.workflow.domain.WfDefinitionConfig;
+import org.dromara.workflow.domain.vo.WfDefinitionConfigVo;
+import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
+
+/**
+ * 娴佺▼瀹氫箟閰嶇疆Mapper鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-18
+ */
+public interface WfDefinitionConfigMapper extends BaseMapperPlus<WfDefinitionConfig, WfDefinitionConfigVo> {
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfFormManageMapper.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfFormManageMapper.java
new file mode 100644
index 0000000..acf8111
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfFormManageMapper.java
@@ -0,0 +1,15 @@
+package org.dromara.workflow.mapper;
+
+import org.dromara.workflow.domain.WfFormManage;
+import org.dromara.workflow.domain.vo.WfFormManageVo;
+import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
+
+/**
+ * 琛ㄥ崟绠$悊Mapper鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-29
+ */
+public interface WfFormManageMapper extends BaseMapperPlus<WfFormManage, WfFormManageVo> {
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfNodeConfigMapper.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfNodeConfigMapper.java
new file mode 100644
index 0000000..d2aecac
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfNodeConfigMapper.java
@@ -0,0 +1,15 @@
+package org.dromara.workflow.mapper;
+
+import org.dromara.workflow.domain.WfNodeConfig;
+import org.dromara.workflow.domain.vo.WfNodeConfigVo;
+import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
+
+/**
+ * 鑺傜偣閰嶇疆Mapper鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-30
+ */
+public interface WfNodeConfigMapper extends BaseMapperPlus<WfNodeConfig, WfNodeConfigVo> {
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfTaskBackNodeMapper.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfTaskBackNodeMapper.java
new file mode 100644
index 0000000..9b291fe
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/mapper/WfTaskBackNodeMapper.java
@@ -0,0 +1,13 @@
+package org.dromara.workflow.mapper;
+
+import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
+import org.dromara.workflow.domain.WfTaskBackNode;
+
+/**
+ * 鑺傜偣椹冲洖璁板綍Mapper鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-13
+ */
+public interface WfTaskBackNodeMapper extends BaseMapperPlus<WfTaskBackNode, WfTaskBackNode> {
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActHiProcinstService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActHiProcinstService.java
new file mode 100644
index 0000000..e802c69
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActHiProcinstService.java
@@ -0,0 +1,31 @@
+package org.dromara.workflow.service;
+
+
+import org.dromara.workflow.domain.ActHiProcinst;
+
+import java.util.List;
+
+/**
+ * 娴佺▼瀹炰緥Service鎺ュ彛
+ *
+ * @author may
+ * @date 2023-07-22
+ */
+public interface IActHiProcinstService {
+
+ /**
+ * 鎸夌収涓氬姟id鏌ヨ
+ *
+ * @param businessKeys 涓氬姟id
+ * @return 缁撴灉
+ */
+ List<ActHiProcinst> selectByBusinessKeyIn(List<String> businessKeys);
+
+ /**
+ * 鎸夌収涓氬姟id鏌ヨ
+ *
+ * @param businessKey 涓氬姟id
+ * @return 缁撴灉
+ */
+ ActHiProcinst selectByBusinessKey(String businessKey);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActHiTaskinstService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActHiTaskinstService.java
new file mode 100644
index 0000000..ad286e2
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActHiTaskinstService.java
@@ -0,0 +1,11 @@
+package org.dromara.workflow.service;
+
+
+/**
+ * 娴佺▼鍘嗗彶浠诲姟Service鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-02
+ */
+public interface IActHiTaskinstService {
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActModelService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActModelService.java
new file mode 100644
index 0000000..4a6d170
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActModelService.java
@@ -0,0 +1,83 @@
+package org.dromara.workflow.service;
+
+import jakarta.servlet.http.HttpServletResponse;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.workflow.domain.bo.ModelBo;
+import org.dromara.workflow.domain.vo.ModelVo;
+import org.flowable.engine.repository.Model;
+
+import java.util.List;
+
+
+/**
+ * 妯″瀷绠$悊 鏈嶅姟灞�
+ *
+ * @author may
+ */
+public interface IActModelService {
+ /**
+ * 鍒嗛〉鏌ヨ妯″瀷
+ *
+ * @param modelBo 妯″瀷鍙傛暟
+ * @param pageQuery 鍙傛暟
+ * @return 杩斿洖鍒嗛〉鍒楄〃
+ */
+ TableDataInfo<Model> page(ModelBo modelBo, PageQuery pageQuery);
+
+ /**
+ * 鏂板妯″瀷
+ *
+ * @param modelBo 妯″瀷璇锋眰瀵硅薄
+ * @return 缁撴灉
+ */
+ boolean saveNewModel(ModelBo modelBo);
+
+ /**
+ * 鏌ヨ妯″瀷
+ *
+ * @param modelId 妯″瀷id
+ * @return 妯″瀷鏁版嵁
+ */
+ ModelVo getInfo(String modelId);
+
+ /**
+ * 淇敼妯″瀷淇℃伅
+ *
+ * @param modelBo 妯″瀷鏁版嵁
+ * @return 缁撴灉
+ */
+ boolean update(ModelBo modelBo);
+
+ /**
+ * 缂栬緫妯″瀷XML
+ *
+ * @param modelBo 妯″瀷鏁版嵁
+ * @return 缁撴灉
+ */
+ boolean editModelXml(ModelBo modelBo);
+
+ /**
+ * 妯″瀷閮ㄧ讲
+ *
+ * @param id 妯″瀷id
+ * @return 缁撴灉
+ */
+ boolean modelDeploy(String id);
+
+ /**
+ * 瀵煎嚭妯″瀷zip鍘嬬缉鍖�
+ *
+ * @param modelIds 妯″瀷id
+ * @param response 鍝嶅簲
+ */
+ void exportZip(List<String> modelIds, HttpServletResponse response);
+
+ /**
+ * 澶嶅埗妯″瀷
+ *
+ * @param modelBo 妯″瀷鏁版嵁
+ * @return 缁撴灉
+ */
+ boolean copyModel(ModelBo modelBo);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActProcessDefinitionService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActProcessDefinitionService.java
new file mode 100644
index 0000000..5d00e41
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActProcessDefinitionService.java
@@ -0,0 +1,91 @@
+package org.dromara.workflow.service;
+
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.workflow.domain.bo.ProcessDefinitionBo;
+import org.dromara.workflow.domain.vo.ProcessDefinitionVo;
+import org.springframework.web.multipart.MultipartFile;
+
+import java.util.List;
+
+/**
+ * 娴佺▼瀹氫箟 鏈嶅姟灞�
+ *
+ * @author may
+ */
+public interface IActProcessDefinitionService {
+ /**
+ * 鍒嗛〉鏌ヨ
+ *
+ * @param processDefinitionBo 鍙傛暟
+ * @param pageQuery 鍒嗛〉
+ * @return 杩斿洖鍒嗛〉鍒楄〃
+ */
+ TableDataInfo<ProcessDefinitionVo> page(ProcessDefinitionBo processDefinitionBo, PageQuery pageQuery);
+
+ /**
+ * 鏌ヨ鍘嗗彶娴佺▼瀹氫箟鍒楄〃
+ *
+ * @param key 娴佺▼瀹氫箟key
+ * @return 缁撴灉
+ */
+ List<ProcessDefinitionVo> getListByKey(String key);
+
+ /**
+ * 鏌ョ湅娴佺▼瀹氫箟鍥剧墖
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ String definitionImage(String processDefinitionId);
+
+ /**
+ * 鏌ョ湅娴佺▼瀹氫箟xml鏂囦欢
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ String definitionXml(String processDefinitionId);
+
+ /**
+ * 鍒犻櫎娴佺▼瀹氫箟
+ *
+ * @param deploymentIds 閮ㄧ讲id
+ * @param processDefinitionIds 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ boolean deleteDeployment(List<String> deploymentIds, List<String> processDefinitionIds);
+
+ /**
+ * 婵�娲绘垨鑰呮寕璧锋祦绋嬪畾涔�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ boolean updateDefinitionState(String processDefinitionId);
+
+ /**
+ * 杩佺Щ娴佺▼瀹氫箟
+ *
+ * @param currentProcessDefinitionId 褰撳墠娴佺▼瀹氫箟id
+ * @param fromProcessDefinitionId 闇�瑕佽縼绉诲埌鐨勬祦绋嬪畾涔塱d
+ * @return 缁撴灉
+ */
+ boolean migrationDefinition(String currentProcessDefinitionId, String fromProcessDefinitionId);
+
+ /**
+ * 娴佺▼瀹氫箟杞崲涓烘ā鍨�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ boolean convertToModel(String processDefinitionId);
+
+ /**
+ * 閫氳繃zip鎴杧ml閮ㄧ讲娴佺▼瀹氫箟
+ *
+ * @param file 鏂囦欢
+ * @param categoryCode 鍒嗙被
+ */
+ void deployByFile(MultipartFile file, String categoryCode);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActProcessInstanceService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActProcessInstanceService.java
new file mode 100644
index 0000000..2fc0c1a
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActProcessInstanceService.java
@@ -0,0 +1,118 @@
+package org.dromara.workflow.service;
+
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.workflow.domain.bo.ProcessInstanceBo;
+import org.dromara.workflow.domain.bo.ProcessInvalidBo;
+import org.dromara.workflow.domain.bo.TaskUrgingBo;
+import org.dromara.workflow.domain.vo.ActHistoryInfoVo;
+import org.dromara.workflow.domain.vo.ProcessInstanceVo;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * 娴佺▼瀹炰緥 鏈嶅姟灞�
+ *
+ * @author may
+ */
+public interface IActProcessInstanceService {
+ /**
+ * 閫氳繃娴佺▼瀹炰緥id鑾峰彇鍘嗗彶娴佺▼鍥�
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ * @return 缁撴灉
+ */
+ String getHistoryImage(String processInstanceId);
+
+ /**
+ * 閫氳繃娴佺▼瀹炰緥id鑾峰彇鍘嗗彶娴佺▼鍥捐繍琛屼腑锛屽巻鍙茬瓑鑺傜偣
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ * @return 缁撴灉
+ */
+ Map<String, Object> getHistoryList(String processInstanceId);
+
+ /**
+ * 鍒嗛〉鏌ヨ姝e湪杩愯鐨勬祦绋嬪疄渚�
+ *
+ * @param processInstanceBo 鍙傛暟
+ * @param pageQuery 鍒嗛〉
+ * @return 缁撴灉
+ */
+ TableDataInfo<ProcessInstanceVo> getPageByRunning(ProcessInstanceBo processInstanceBo, PageQuery pageQuery);
+
+ /**
+ * 鍒嗛〉鏌ヨ宸茬粨鏉熺殑娴佺▼瀹炰緥
+ *
+ * @param processInstanceBo 鍙傛暟
+ * @param pageQuery 鍒嗛〉
+ * @return 缁撴灉
+ */
+ TableDataInfo<ProcessInstanceVo> getPageByFinish(ProcessInstanceBo processInstanceBo, PageQuery pageQuery);
+
+ /**
+ * 鑾峰彇瀹℃壒璁板綍
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ * @return 缁撴灉
+ */
+ List<ActHistoryInfoVo> getHistoryRecord(String processInstanceId);
+
+ /**
+ * 浣滃簾娴佺▼瀹炰緥锛屼笉浼氬垹闄ゅ巻鍙茶褰�(鍒犻櫎杩愯涓殑瀹炰緥)
+ *
+ * @param processInvalidBo 鍙傛暟
+ * @return 缁撴灉
+ */
+ boolean deleteRunInstance(ProcessInvalidBo processInvalidBo);
+
+ /**
+ * 杩愯涓殑瀹炰緥 鍒犻櫎绋嬪疄渚嬶紝鍒犻櫎鍘嗗彶璁板綍锛屽垹闄や笟鍔′笌娴佺▼鍏宠仈淇℃伅
+ *
+ * @param processInstanceIds 娴佺▼瀹炰緥id
+ * @return 缁撴灉
+ */
+ boolean deleteRunAndHisInstance(List<String> processInstanceIds);
+
+ /**
+ * 鎸夌収涓氬姟id鍒犻櫎 杩愯涓殑瀹炰緥 鍒犻櫎绋嬪疄渚嬶紝鍒犻櫎鍘嗗彶璁板綍锛屽垹闄や笟鍔′笌娴佺▼鍏宠仈淇℃伅
+ *
+ * @param businessKeys 涓氬姟id
+ * @return 缁撴灉
+ */
+ boolean deleteRunAndHisInstanceByBusinessKeys(List<String> businessKeys);
+
+ /**
+ * 宸插畬鎴愮殑瀹炰緥 鍒犻櫎绋嬪疄渚嬶紝鍒犻櫎鍘嗗彶璁板綍锛屽垹闄や笟鍔′笌娴佺▼鍏宠仈淇℃伅
+ *
+ * @param processInstanceIds 娴佺▼瀹炰緥id
+ * @return 缁撴灉
+ */
+ boolean deleteFinishAndHisInstance(List<String> processInstanceIds);
+
+ /**
+ * 鎾ら攢娴佺▼鐢宠
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ * @return 缁撴灉
+ */
+ boolean cancelProcessApply(String processInstanceId);
+
+ /**
+ * 鍒嗛〉鏌ヨ褰撳墠鐧诲綍浜哄崟鎹�
+ *
+ * @param processInstanceBo 鍙傛暟
+ * @param pageQuery 鍒嗛〉
+ * @return 缁撴灉
+ */
+ TableDataInfo<ProcessInstanceVo> getPageByCurrent(ProcessInstanceBo processInstanceBo, PageQuery pageQuery);
+
+ /**
+ * 浠诲姟鍌姙(缁欏綋鍓嶄换鍔″姙鐞嗕汉鍙戦�佺珯鍐呬俊锛岄偖浠讹紝鐭俊绛�)
+ *
+ * @param taskUrgingBo 浠诲姟鍌姙
+ * @return 缁撴灉
+ */
+ boolean taskUrging(TaskUrgingBo taskUrgingBo);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActTaskService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActTaskService.java
new file mode 100644
index 0000000..8e9f763
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IActTaskService.java
@@ -0,0 +1,161 @@
+package org.dromara.workflow.service;
+
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.workflow.domain.bo.*;
+import org.dromara.workflow.domain.vo.TaskVo;
+import org.dromara.workflow.domain.vo.VariableVo;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * 浠诲姟 鏈嶅姟灞�
+ *
+ * @author may
+ */
+public interface IActTaskService {
+ /**
+ * 鍚姩浠诲姟
+ *
+ * @param startProcessBo 鍚姩娴佺▼鍙傛暟
+ * @return 缁撴灉
+ */
+ Map<String, Object> startWorkFlow(StartProcessBo startProcessBo);
+
+
+ /**
+ * 鍔炵悊浠诲姟
+ *
+ * @param completeTaskBo 鍔炵悊浠诲姟鍙傛暟
+ * @return 缁撴灉
+ */
+ boolean completeTask(CompleteTaskBo completeTaskBo);
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勫緟鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ * @param pageQuery 鍒嗛〉
+ * @return 缁撴灉
+ */
+ TableDataInfo<TaskVo> getPageByTaskWait(TaskBo taskBo, PageQuery pageQuery);
+
+ /**
+ * 鏌ヨ褰撳墠绉熸埛鎵�鏈夊緟鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ * @param pageQuery 鍒嗛〉
+ * @return 缁撴灉
+ */
+ TableDataInfo<TaskVo> getPageByAllTaskWait(TaskBo taskBo, PageQuery pageQuery);
+
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勫凡鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ * @param pageQuery 鍙傛暟
+ * @return 缁撴灉
+ */
+ TableDataInfo<TaskVo> getPageByTaskFinish(TaskBo taskBo, PageQuery pageQuery);
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勬妱閫�
+ *
+ * @param taskBo 鍙傛暟
+ * @param pageQuery 鍙傛暟
+ * @return 缁撴灉
+ */
+ TableDataInfo<TaskVo> getPageByTaskCopy(TaskBo taskBo, PageQuery pageQuery);
+
+ /**
+ * 鏌ヨ褰撳墠绉熸埛鎵�鏈夊凡鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ * @param pageQuery 鍙傛暟
+ * @return 缁撴灉
+ */
+ TableDataInfo<TaskVo> getPageByAllTaskFinish(TaskBo taskBo, PageQuery pageQuery);
+
+ /**
+ * 濮旀淳浠诲姟
+ *
+ * @param delegateBo 鍙傛暟
+ * @return 缁撴灉
+ */
+ boolean delegateTask(DelegateBo delegateBo);
+
+ /**
+ * 缁堟浠诲姟
+ *
+ * @param terminationBo 鍙傛暟
+ * @return 缁撴灉
+ */
+ boolean terminationTask(TerminationBo terminationBo);
+
+ /**
+ * 杞姙浠诲姟
+ *
+ * @param transmitBo 鍙傛暟
+ * @return 缁撴灉
+ */
+ boolean transferTask(TransmitBo transmitBo);
+
+ /**
+ * 浼氱浠诲姟鍔犵
+ *
+ * @param addMultiBo 鍙傛暟
+ * @return 缁撴灉
+ */
+ boolean addMultiInstanceExecution(AddMultiBo addMultiBo);
+
+ /**
+ * 浼氱浠诲姟鍑忕
+ *
+ * @param deleteMultiBo 鍙傛暟
+ * @return 缁撴灉
+ */
+ boolean deleteMultiInstanceExecution(DeleteMultiBo deleteMultiBo);
+
+ /**
+ * 椹冲洖瀹℃壒
+ *
+ * @param backProcessBo 鍙傛暟
+ * @return 娴佺▼瀹炰緥id
+ */
+ String backProcess(BackProcessBo backProcessBo);
+
+ /**
+ * 淇敼浠诲姟鍔炵悊浜�
+ *
+ * @param taskIds 浠诲姟id
+ * @param userId 鍔炵悊浜篿d
+ * @return 缁撴灉
+ */
+ boolean updateAssignee(String[] taskIds, String userId);
+
+ /**
+ * 鏌ヨ娴佺▼鍙橀噺
+ *
+ * @param taskId 浠诲姟id
+ * @return 缁撴灉
+ */
+ List<VariableVo> getInstanceVariable(String taskId);
+
+ /**
+ * 鏌ヨ宸ヤ綔娴佷换鍔$敤鎴烽�夋嫨鍔犵浜哄憳
+ *
+ * @param taskId 浠诲姟id
+ * @return 缁撴灉
+ */
+ String getTaskUserIdsByAddMultiInstance(String taskId);
+
+ /**
+ * 鏌ヨ宸ヤ綔娴侀�夋嫨鍑忕浜哄憳
+ *
+ * @param taskId 浠诲姟id
+ * @return 缁撴灉
+ */
+ List<TaskVo> getListByDeleteMultiInstance(String taskId);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/ITestLeaveService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/ITestLeaveService.java
new file mode 100644
index 0000000..5c95547
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/ITestLeaveService.java
@@ -0,0 +1,49 @@
+package org.dromara.workflow.service;
+
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.workflow.domain.TestLeave;
+import org.dromara.workflow.domain.bo.TestLeaveBo;
+import org.dromara.workflow.domain.vo.TestLeaveVo;
+
+import java.util.Collection;
+import java.util.List;
+
+/**
+ * 璇峰亣Service鎺ュ彛
+ *
+ * @author may
+ * @date 2023-07-21
+ */
+public interface ITestLeaveService {
+
+ /**
+ * 鏌ヨ璇峰亣
+ */
+ TestLeaveVo queryById(Long id);
+
+ /**
+ * 鏌ヨ璇峰亣鍒楄〃
+ */
+ TableDataInfo<TestLeaveVo> queryPageList(TestLeaveBo bo, PageQuery pageQuery);
+
+ /**
+ * 鏌ヨ璇峰亣鍒楄〃
+ */
+ List<TestLeaveVo> queryList(TestLeaveBo bo);
+
+ /**
+ * 鏂板璇峰亣
+ */
+ TestLeaveVo insertByBo(TestLeaveBo bo);
+
+ /**
+ * 淇敼璇峰亣
+ */
+ TestLeaveVo updateByBo(TestLeaveBo bo);
+
+ /**
+ * 鏍¢獙骞舵壒閲忓垹闄よ鍋囦俊鎭�
+ */
+ Boolean deleteWithValidByIds(Collection<Long> ids);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfCategoryService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfCategoryService.java
new file mode 100644
index 0000000..acf0aa2
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfCategoryService.java
@@ -0,0 +1,51 @@
+package org.dromara.workflow.service;
+
+import org.dromara.workflow.domain.WfCategory;
+import org.dromara.workflow.domain.bo.WfCategoryBo;
+import org.dromara.workflow.domain.vo.WfCategoryVo;
+
+import java.util.Collection;
+import java.util.List;
+
+/**
+ * 娴佺▼鍒嗙被Service鎺ュ彛
+ *
+ * @author may
+ * @date 2023-06-28
+ */
+public interface IWfCategoryService {
+
+ /**
+ * 鏌ヨ娴佺▼鍒嗙被
+ */
+ WfCategoryVo queryById(Long id);
+
+
+ /**
+ * 鏌ヨ娴佺▼鍒嗙被鍒楄〃
+ */
+ List<WfCategoryVo> queryList(WfCategoryBo bo);
+
+ /**
+ * 鏂板娴佺▼鍒嗙被
+ */
+ Boolean insertByBo(WfCategoryBo bo);
+
+ /**
+ * 淇敼娴佺▼鍒嗙被
+ */
+ Boolean updateByBo(WfCategoryBo bo);
+
+ /**
+ * 鏍¢獙骞舵壒閲忓垹闄ゆ祦绋嬪垎绫讳俊鎭�
+ */
+ Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid);
+
+ /**
+ * 鎸夌収绫诲埆缂栫爜鏌ヨ
+ *
+ * @param categoryCode 鍒嗙被姣斿悧
+ * @return 缁撴灉
+ */
+ WfCategory queryByCategoryCode(String categoryCode);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfDefinitionConfigService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfDefinitionConfigService.java
new file mode 100644
index 0000000..fe5cf7a
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfDefinitionConfigService.java
@@ -0,0 +1,83 @@
+package org.dromara.workflow.service;
+
+import org.dromara.workflow.domain.vo.WfDefinitionConfigVo;
+import org.dromara.workflow.domain.bo.WfDefinitionConfigBo;
+
+import java.util.Collection;
+import java.util.List;
+
+/**
+ * 娴佺▼瀹氫箟閰嶇疆Service鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-18
+ */
+public interface IWfDefinitionConfigService {
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆
+ *
+ * @param definitionId 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ WfDefinitionConfigVo getByDefId(String definitionId);
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆
+ *
+ * @param tableName 琛ㄥ悕
+ * @return 缁撴灉
+ */
+ WfDefinitionConfigVo getByTableNameLastVersion(String tableName);
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆
+ *
+ * @param definitionId 娴佺▼瀹氫箟id
+ * @param tableName 琛ㄥ悕
+ * @return 缁撴灉
+ */
+ WfDefinitionConfigVo getByDefIdAndTableName(String definitionId, String tableName);
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆鎺掗櫎褰撳墠鏌ヨ鐨勬祦绋嬪畾涔�
+ *
+ * @param definitionId 娴佺▼瀹氫箟id
+ * @param tableName 琛ㄥ悕
+ * @return 缁撴灉
+ */
+ List<WfDefinitionConfigVo> getByTableNameNotDefId(String tableName, String definitionId);
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆鍒楄〃
+ *
+ * @param definitionIds 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ List<WfDefinitionConfigVo> queryList(List<String> definitionIds);
+
+
+ /**
+ * 鏂板娴佺▼瀹氫箟閰嶇疆
+ *
+ * @param bo 鍙傛暟
+ * @return 缁撴灉
+ */
+ Boolean saveOrUpdate(WfDefinitionConfigBo bo);
+
+ /**
+ * 鍒犻櫎
+ *
+ * @param ids id
+ * @return 缁撴灉
+ */
+ Boolean deleteByIds(Collection<Long> ids);
+
+ /**
+ * 鎸夌収娴佺▼瀹氫箟id鍒犻櫎
+ *
+ * @param ids 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ Boolean deleteByDefIds(Collection<String> ids);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfFormManageService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfFormManageService.java
new file mode 100644
index 0000000..2ca2264
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfFormManageService.java
@@ -0,0 +1,81 @@
+package org.dromara.workflow.service;
+
+import org.dromara.workflow.domain.vo.WfFormManageVo;
+import org.dromara.workflow.domain.bo.WfFormManageBo;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.mybatis.core.page.PageQuery;
+
+import java.util.Collection;
+import java.util.List;
+
+/**
+ * 琛ㄥ崟绠$悊Service鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-29
+ */
+public interface IWfFormManageService {
+
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊
+ *
+ * @param id 涓婚敭
+ * @return 缁撴灉
+ */
+ WfFormManageVo queryById(Long id);
+
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊
+ *
+ * @param ids 涓婚敭
+ * @return 缁撴灉
+ */
+ List<WfFormManageVo> queryByIds(List<Long> ids);
+
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊鍒楄〃
+ *
+ * @param bo 鍙傛暟
+ * @param pageQuery 鍒嗛〉
+ * @return 缁撴灉
+ */
+ TableDataInfo<WfFormManageVo> queryPageList(WfFormManageBo bo, PageQuery pageQuery);
+
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊鍒楄〃
+ *
+ * @return 缁撴灉
+ */
+ List<WfFormManageVo> selectList();
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊鍒楄〃
+ *
+ * @param bo 鍙傛暟
+ * @return 缁撴灉
+ */
+ List<WfFormManageVo> queryList(WfFormManageBo bo);
+
+ /**
+ * 鏂板琛ㄥ崟绠$悊
+ *
+ * @param bo 鍙傛暟
+ * @return 缁撴灉
+ */
+ Boolean insertByBo(WfFormManageBo bo);
+
+ /**
+ * 淇敼琛ㄥ崟绠$悊
+ *
+ * @param bo 鍙傛暟
+ * @return 缁撴灉
+ */
+ Boolean updateByBo(WfFormManageBo bo);
+
+ /**
+ * 鎵归噺鍒犻櫎琛ㄥ崟绠$悊淇℃伅
+ *
+ * @param ids 涓婚敭
+ * @return 缁撴灉
+ */
+ Boolean deleteByIds(Collection<Long> ids);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfNodeConfigService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfNodeConfigService.java
new file mode 100644
index 0000000..5e64d64
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfNodeConfigService.java
@@ -0,0 +1,56 @@
+package org.dromara.workflow.service;
+
+import org.dromara.workflow.domain.WfNodeConfig;
+import org.dromara.workflow.domain.vo.WfNodeConfigVo;
+
+import java.util.Collection;
+import java.util.List;
+
+/**
+ * 鑺傜偣閰嶇疆Service鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-30
+ */
+public interface IWfNodeConfigService {
+
+ /**
+ * 鏌ヨ鑺傜偣閰嶇疆
+ *
+ * @param id 涓婚敭
+ * @return 缁撴灉
+ */
+ WfNodeConfigVo queryById(Long id);
+
+ /**
+ * 淇濆瓨鑺傜偣閰嶇疆
+ *
+ * @param list 鍙傛暟
+ * @return 缁撴灉
+ */
+ Boolean saveOrUpdate(List<WfNodeConfig> list);
+
+ /**
+ * 鎵归噺鍒犻櫎鑺傜偣閰嶇疆淇℃伅
+ *
+ * @param ids 涓婚敭
+ * @return 缁撴灉
+ */
+ Boolean deleteByIds(Collection<Long> ids);
+
+ /**
+ * 鎸夌収娴佺▼瀹氫箟id鍒犻櫎
+ *
+ * @param ids 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ Boolean deleteByDefIds(Collection<String> ids);
+
+ /**
+ * 鎸夌収娴佺▼瀹氫箟id鏌ヨ
+ *
+ * @param ids 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ List<WfNodeConfigVo> selectByDefIds(Collection<String> ids);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfTaskBackNodeService.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfTaskBackNodeService.java
new file mode 100644
index 0000000..97f9406
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/IWfTaskBackNodeService.java
@@ -0,0 +1,65 @@
+package org.dromara.workflow.service;
+
+
+import org.dromara.workflow.domain.WfTaskBackNode;
+import org.flowable.task.api.Task;
+
+import java.util.List;
+
+/**
+ * 鑺傜偣椹冲洖璁板綍Service鎺ュ彛
+ *
+ * @author may
+ * @date 2024-03-13
+ */
+public interface IWfTaskBackNodeService {
+
+ /**
+ * 璁板綍瀹℃壒鑺傜偣
+ *
+ * @param task 浠诲姟
+ */
+ void recordExecuteNode(Task task);
+
+ /**
+ * 鎸夋祦绋嬪疄渚媔d鏌ヨ
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ * @return 缁撴灉
+ */
+ List<WfTaskBackNode> getListByInstanceId(String processInstanceId);
+
+ /**
+ * 鎸夌収娴佺▼瀹炰緥id锛岃妭鐐筰d鏌ヨ
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ * @param nodeId 鑺傜偣id
+ * @return 缁撴灉
+ */
+ WfTaskBackNode getListByInstanceIdAndNodeId(String processInstanceId, String nodeId);
+
+ /**
+ * 鍒犻櫎椹冲洖鍚庣殑鑺傜偣
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ * @param targetActivityId 鑺傜偣id
+ * @return 缁撴灉
+ */
+ boolean deleteBackTaskNode(String processInstanceId, String targetActivityId);
+
+ /**
+ * 鎸夋祦绋嬪疄渚媔d鍒犻櫎
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ * @return 缁撴灉
+ */
+ boolean deleteByInstanceId(String processInstanceId);
+
+ /**
+ * 鎸夋祦绋嬪疄渚媔d鍒犻櫎
+ *
+ * @param processInstanceIds 娴佺▼瀹炰緥id
+ * @return 缁撴灉
+ */
+ boolean deleteByInstanceIds(List<String> processInstanceIds);
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActHiProcinstServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActHiProcinstServiceImpl.java
new file mode 100644
index 0000000..06d607b
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActHiProcinstServiceImpl.java
@@ -0,0 +1,51 @@
+package org.dromara.workflow.service.impl;
+
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.tenant.helper.TenantHelper;
+import org.dromara.workflow.domain.ActHiProcinst;
+import org.dromara.workflow.mapper.ActHiProcinstMapper;
+import org.dromara.workflow.service.IActHiProcinstService;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+
+
+/**
+ * 娴佺▼瀹炰緥Service涓氬姟灞傚鐞�
+ *
+ * @author may
+ * @date 2023-07-22
+ */
+@RequiredArgsConstructor
+@Service
+public class ActHiProcinstServiceImpl implements IActHiProcinstService {
+
+ private final ActHiProcinstMapper baseMapper;
+
+ /**
+ * 鎸夌収涓氬姟id鏌ヨ
+ *
+ * @param businessKeys 涓氬姟id
+ */
+ @Override
+ public List<ActHiProcinst> selectByBusinessKeyIn(List<String> businessKeys) {
+ return baseMapper.selectList(new LambdaQueryWrapper<ActHiProcinst>()
+ .in(ActHiProcinst::getBusinessKey, businessKeys)
+ .eq(TenantHelper.isEnable(), ActHiProcinst::getTenantId, TenantHelper.getTenantId()));
+ }
+
+ /**
+ * 鎸夌収涓氬姟id鏌ヨ
+ *
+ * @param businessKey 涓氬姟id
+ */
+ @Override
+ public ActHiProcinst selectByBusinessKey(String businessKey) {
+ return baseMapper.selectOne(new LambdaQueryWrapper<ActHiProcinst>()
+ .eq(ActHiProcinst::getBusinessKey, businessKey)
+ .eq(TenantHelper.isEnable(), ActHiProcinst::getTenantId, TenantHelper.getTenantId()));
+
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActHiTaskinstServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActHiTaskinstServiceImpl.java
new file mode 100644
index 0000000..5548f22
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActHiTaskinstServiceImpl.java
@@ -0,0 +1,18 @@
+package org.dromara.workflow.service.impl;
+
+import lombok.RequiredArgsConstructor;
+import org.springframework.stereotype.Service;
+import org.dromara.workflow.service.IActHiTaskinstService;
+
+
+/**
+ * 娴佺▼鍘嗗彶浠诲姟Service涓氬姟灞傚鐞�
+ *
+ * @author may
+ * @date 2024-03-02
+ */
+@RequiredArgsConstructor
+@Service
+public class ActHiTaskinstServiceImpl implements IActHiTaskinstService {
+
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActModelServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActModelServiceImpl.java
new file mode 100644
index 0000000..7ea53d8
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActModelServiceImpl.java
@@ -0,0 +1,424 @@
+package org.dromara.workflow.service.impl;
+
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.lang.Validator;
+import cn.hutool.core.util.ArrayUtil;
+import cn.hutool.core.util.ObjectUtil;
+import cn.hutool.core.util.StrUtil;
+import cn.hutool.core.util.ZipUtil;
+import cn.hutool.json.JSONUtil;
+import com.alibaba.excel.util.StringUtils;
+import jakarta.servlet.http.HttpServletResponse;
+import lombok.RequiredArgsConstructor;
+import org.apache.batik.transcoder.TranscoderInput;
+import org.apache.batik.transcoder.TranscoderOutput;
+import org.apache.batik.transcoder.image.PNGTranscoder;
+import org.dromara.common.core.exception.ServiceException;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.tenant.helper.TenantHelper;
+import org.dromara.workflow.common.constant.FlowConstant;
+import org.dromara.workflow.domain.WfNodeConfig;
+import org.dromara.workflow.domain.bo.ModelBo;
+import org.dromara.workflow.domain.bo.WfDefinitionConfigBo;
+import org.dromara.workflow.domain.vo.ModelVo;
+import org.dromara.workflow.domain.vo.WfDefinitionConfigVo;
+import org.dromara.workflow.service.IActModelService;
+import org.dromara.workflow.service.IWfDefinitionConfigService;
+import org.dromara.workflow.service.IWfNodeConfigService;
+import org.dromara.workflow.utils.ModelUtils;
+import org.dromara.workflow.utils.QueryUtils;
+import org.flowable.bpmn.converter.BpmnXMLConverter;
+import org.flowable.bpmn.model.BpmnModel;
+import org.flowable.bpmn.model.Process;
+import org.flowable.bpmn.model.UserTask;
+import org.flowable.engine.RepositoryService;
+import org.flowable.engine.repository.Deployment;
+import org.flowable.engine.repository.Model;
+import org.flowable.engine.repository.ModelQuery;
+import org.flowable.engine.repository.ProcessDefinition;
+import org.flowable.validation.ValidationError;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.URLEncoder;
+import java.nio.charset.StandardCharsets;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+import java.util.stream.Collectors;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipOutputStream;
+
+/**
+ * 妯″瀷绠$悊 鏈嶅姟灞傚疄鐜�
+ *
+ * @author may
+ */
+@RequiredArgsConstructor
+@Service
+public class ActModelServiceImpl implements IActModelService {
+
+ private final RepositoryService repositoryService;
+ private final IWfNodeConfigService wfNodeConfigService;
+ private final IWfDefinitionConfigService wfDefinitionConfigService;
+
+ /**
+ * 鍒嗛〉鏌ヨ妯″瀷
+ *
+ * @param modelBo 妯″瀷鍙傛暟
+ * @return 杩斿洖鍒嗛〉鍒楄〃
+ */
+ @Override
+ public TableDataInfo<Model> page(ModelBo modelBo, PageQuery pageQuery) {
+ ModelQuery query = QueryUtils.modelQuery();
+ if (StringUtils.isNotBlank(modelBo.getName())) {
+ query.modelNameLike("%" + modelBo.getName() + "%");
+ }
+ if (StringUtils.isNotBlank(modelBo.getKey())) {
+ query.modelKey(modelBo.getKey());
+ }
+ if (StringUtils.isNotBlank(modelBo.getCategoryCode())) {
+ query.modelCategory(modelBo.getCategoryCode());
+ }
+ query.orderByLastUpdateTime().desc();
+ // 鍒涘缓鏃堕棿闄嶅簭鎺掑垪
+ query.orderByCreateTime().desc();
+ // 鍒嗛〉鏌ヨ
+ List<Model> modelList = query.listPage(pageQuery.getFirstNum(), pageQuery.getPageSize());
+ // 鎬昏褰曟暟
+ long total = query.count();
+ TableDataInfo<Model> build = TableDataInfo.build();
+ build.setRows(modelList);
+ build.setTotal(total);
+ return build;
+ }
+
+ /**
+ * 鏂板妯″瀷
+ *
+ * @param modelBo 妯″瀷璇锋眰瀵硅薄
+ * @return 缁撴灉
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean saveNewModel(ModelBo modelBo) {
+ try {
+ int version = 0;
+ String key = modelBo.getKey();
+ String name = modelBo.getName();
+ String description = modelBo.getDescription();
+ String categoryCode = modelBo.getCategoryCode();
+ String xml = modelBo.getXml();
+ Model checkModel = QueryUtils.modelQuery().modelKey(key).singleResult();
+ if (ObjectUtil.isNotNull(checkModel)) {
+ throw new ServiceException("妯″瀷key宸插瓨鍦紒");
+ }
+ //鍒濆绌虹殑妯″瀷
+ Model model = repositoryService.newModel();
+ model.setKey(key);
+ model.setName(name);
+ model.setVersion(version);
+ model.setCategory(categoryCode);
+ model.setMetaInfo(description);
+ model.setTenantId(TenantHelper.getTenantId());
+ //淇濆瓨鍒濆鍖栫殑妯″瀷鍩烘湰淇℃伅鏁版嵁
+ repositoryService.saveModel(model);
+ repositoryService.addModelEditorSource(model.getId(), StrUtil.utf8Bytes(xml));
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 鏌ヨ妯″瀷
+ *
+ * @param id 妯″瀷id
+ * @return 妯″瀷鏁版嵁
+ */
+ @Override
+ public ModelVo getInfo(String id) {
+ ModelVo modelVo = new ModelVo();
+ Model model = repositoryService.getModel(id);
+ if (model != null) {
+ try {
+ byte[] modelEditorSource = repositoryService.getModelEditorSource(model.getId());
+ modelVo.setXml(StrUtil.utf8Str(modelEditorSource));
+ modelVo.setId(model.getId());
+ modelVo.setKey(model.getKey());
+ modelVo.setName(model.getName());
+ modelVo.setCategoryCode(model.getCategory());
+ modelVo.setDescription(model.getMetaInfo());
+ return modelVo;
+ } catch (Exception e) {
+ throw new ServiceException(e.getMessage());
+ }
+ }
+ return modelVo;
+ }
+
+ /**
+ * 淇敼妯″瀷淇℃伅
+ *
+ * @param modelBo 妯″瀷鏁版嵁
+ * @return 缁撴灉
+ */
+ @Override
+ public boolean update(ModelBo modelBo) {
+ try {
+ Model model = repositoryService.getModel(modelBo.getId());
+ List<Model> list = QueryUtils.modelQuery().modelKey(modelBo.getKey()).list();
+ list.stream().filter(e -> !e.getId().equals(model.getId())).findFirst().ifPresent(e -> {
+ throw new ServiceException("妯″瀷KEY宸插瓨鍦紒");
+ });
+ model.setCategory(modelBo.getCategoryCode());
+ model.setMetaInfo(modelBo.getDescription());
+ repositoryService.saveModel(model);
+ } catch (Exception e) {
+ throw new ServiceException(e.getMessage());
+ }
+ return true;
+ }
+
+ /**
+ * 缂栬緫妯″瀷XML
+ *
+ * @param modelBo 妯″瀷鏁版嵁
+ * @return 缁撴灉
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean editModelXml(ModelBo modelBo) {
+ try {
+ String xml = modelBo.getXml();
+ String svg = modelBo.getSvg();
+ String modelId = modelBo.getId();
+ String key = modelBo.getKey();
+ String name = modelBo.getName();
+ BpmnModel bpmnModel = ModelUtils.xmlToBpmnModel(xml);
+ ModelUtils.checkBpmnModel(bpmnModel);
+ Model model = repositoryService.getModel(modelId);
+ List<Model> list = QueryUtils.modelQuery().modelKey(key).list();
+ list.stream().filter(e -> !e.getId().equals(model.getId())).findFirst().ifPresent(e -> {
+ throw new ServiceException("妯″瀷KEY宸插瓨鍦紒");
+ });
+ // 鏍¢獙key鍛藉悕瑙勮寖
+ if (!Validator.isMatchRegex(FlowConstant.MODEL_KEY_PATTERN, key)) {
+ throw new ServiceException("妯″瀷鏍囪瘑KEY鍙兘瀛楃鎴栬�呬笅鍒掔嚎寮�澶达紒");
+ }
+ model.setKey(key);
+ model.setName(name);
+ model.setVersion(model.getVersion() + 1);
+ repositoryService.saveModel(model);
+ repositoryService.addModelEditorSource(model.getId(), StrUtil.utf8Bytes(xml));
+ // 杞崲鍥剧墖
+ InputStream svgStream = new ByteArrayInputStream(StrUtil.utf8Bytes(svg));
+ TranscoderInput input = new TranscoderInput(svgStream);
+
+ PNGTranscoder transcoder = new PNGTranscoder();
+ ByteArrayOutputStream outStream = new ByteArrayOutputStream();
+ TranscoderOutput output = new TranscoderOutput(outStream);
+
+ transcoder.transcode(input, output);
+ final byte[] result = outStream.toByteArray();
+ repositoryService.addModelEditorSourceExtra(model.getId(), result);
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 妯″瀷閮ㄧ讲
+ *
+ * @param id 妯″瀷id
+ * @return 缁撴灉
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean modelDeploy(String id) {
+ try {
+ // 鏌ヨ娴佺▼瀹氫箟妯″瀷xml
+ byte[] xmlBytes = repositoryService.getModelEditorSource(id);
+ if (ArrayUtil.isEmpty(xmlBytes)) {
+ throw new ServiceException("妯″瀷鏁版嵁涓虹┖锛岃鍏堣璁℃祦绋嬪畾涔夋ā鍨嬶紝鍐嶈繘琛岄儴缃诧紒");
+ }
+ if (JSONUtil.isTypeJSON(new String(xmlBytes, StandardCharsets.UTF_8))) {
+ byte[] bytes = ModelUtils.bpmnJsonToXmlBytes(xmlBytes);
+ if (ArrayUtil.isEmpty(bytes)) {
+ throw new ServiceException("妯″瀷涓嶈兘涓虹┖锛岃鑷冲皯璁捐涓�鏉′富绾挎祦绋嬶紒");
+ }
+ }
+ BpmnModel bpmnModel = ModelUtils.xmlToBpmnModel(xmlBytes);
+ // 鏍¢獙妯″瀷
+ ModelUtils.checkBpmnModel(bpmnModel);
+ List<ValidationError> validationErrors = repositoryService.validateProcess(bpmnModel);
+ if (CollUtil.isNotEmpty(validationErrors)) {
+ String errorMsg = validationErrors.stream().map(ValidationError::getProblem).distinct().collect(Collectors.joining(","));
+ throw new ServiceException(errorMsg);
+ }
+ // 鏌ヨ妯″瀷鐨勫熀鏈俊鎭�
+ Model model = repositoryService.getModel(id);
+ ProcessDefinition processDefinition = QueryUtils.definitionQuery().processDefinitionKey(model.getKey()).latestVersion().singleResult();
+ // xml璧勬簮鐨勫悕绉� 锛屽搴攁ct_ge_bytearray琛ㄤ腑鐨刵ame_瀛楁
+ String processName = model.getName() + ".bpmn20.xml";
+ // 璋冪敤閮ㄧ讲鐩稿叧鐨刟pi鏂规硶杩涜閮ㄧ讲娴佺▼瀹氫箟
+ Deployment deployment = repositoryService.createDeployment()
+ // 閮ㄧ讲鍚嶇О
+ .name(model.getName())
+ // 閮ㄧ讲鏍囪瘑key
+ .key(model.getKey())
+ // 閮ㄧ讲娴佺▼鍒嗙被
+ .category(model.getCategory())
+ // bpmn20.xml璧勬簮
+ .addBytes(processName, xmlBytes)
+ // 绉熸埛id
+ .tenantId(TenantHelper.getTenantId())
+ .deploy();
+
+ // 鏇存柊 閮ㄧ讲id 鍒版祦绋嬪畾涔夋ā鍨嬫暟鎹〃涓�
+ model.setDeploymentId(deployment.getId());
+ repositoryService.saveModel(model);
+ // 鏇存柊鍒嗙被
+ ProcessDefinition definition = QueryUtils.definitionQuery().deploymentId(deployment.getId()).singleResult();
+ repositoryService.setProcessDefinitionCategory(definition.getId(), model.getCategory());
+ //鏇存柊娴佺▼瀹氫箟閰嶇疆
+ if (processDefinition != null) {
+ WfDefinitionConfigVo definitionVo = wfDefinitionConfigService.getByDefId(processDefinition.getId());
+ if (definitionVo != null) {
+ wfDefinitionConfigService.deleteByDefIds(Collections.singletonList(processDefinition.getId()));
+ WfDefinitionConfigBo wfFormDefinition = new WfDefinitionConfigBo();
+ wfFormDefinition.setDefinitionId(definition.getId());
+ wfFormDefinition.setProcessKey(definition.getKey());
+ wfFormDefinition.setTableName(definitionVo.getTableName());
+ wfFormDefinition.setVersion(definition.getVersion());
+ wfFormDefinition.setRemark(definitionVo.getRemark());
+ wfDefinitionConfigService.saveOrUpdate(wfFormDefinition);
+ }
+ }
+ //鏇存柊娴佺▼鑺傜偣閰嶇疆琛ㄥ崟
+ List<UserTask> userTasks = ModelUtils.getUserTaskFlowElements(definition.getId());
+ UserTask applyUserTask = ModelUtils.getApplyUserTask(definition.getId());
+ List<WfNodeConfig> wfNodeConfigList = new ArrayList<>();
+ for (UserTask userTask : userTasks) {
+ if (StringUtils.isNotBlank(userTask.getFormKey()) && userTask.getFormKey().contains(StrUtil.COLON)) {
+ WfNodeConfig wfNodeConfig = new WfNodeConfig();
+ wfNodeConfig.setNodeId(userTask.getId());
+ wfNodeConfig.setNodeName(userTask.getName());
+ wfNodeConfig.setDefinitionId(definition.getId());
+ String[] split = userTask.getFormKey().split(StrUtil.COLON);
+ wfNodeConfig.setFormType(split[0]);
+ wfNodeConfig.setFormId(Long.valueOf(split[1]));
+ wfNodeConfig.setApplyUserTask(applyUserTask.getId().equals(userTask.getId()) ? FlowConstant.TRUE : FlowConstant.FALSE);
+ wfNodeConfigList.add(wfNodeConfig);
+ }
+ }
+ if (CollUtil.isNotEmpty(wfNodeConfigList)) {
+ wfNodeConfigService.saveOrUpdate(wfNodeConfigList);
+ }
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 瀵煎嚭妯″瀷zip鍘嬬缉鍖�
+ *
+ * @param modelIds 妯″瀷id
+ * @param response 鐩稿簲
+ */
+ @Override
+ public void exportZip(List<String> modelIds, HttpServletResponse response) {
+ try (ZipOutputStream zos = ZipUtil.getZipOutputStream(response.getOutputStream(), StandardCharsets.UTF_8)) {
+ // 鍘嬬缉鍖呮枃浠跺悕
+ String zipName = "妯″瀷涓嶅瓨鍦�";
+ // 鏌ヨ妯″瀷鍩烘湰淇℃伅
+ for (String modelId : modelIds) {
+ Model model = repositoryService.getModel(modelId);
+ byte[] xmlBytes = repositoryService.getModelEditorSource(modelId);
+ if (ObjectUtil.isNotNull(model)) {
+ if (JSONUtil.isTypeJSON(new String(xmlBytes, StandardCharsets.UTF_8)) && ArrayUtil.isEmpty(ModelUtils.bpmnJsonToXmlBytes(xmlBytes))) {
+ zipName = "妯″瀷涓嶈兘涓虹┖锛岃鑷冲皯璁捐涓�鏉′富绾挎祦绋嬶紒";
+ zos.putNextEntry(new ZipEntry(zipName + ".txt"));
+ zos.write(zipName.getBytes(StandardCharsets.UTF_8));
+ } else if (ArrayUtil.isEmpty(xmlBytes)) {
+ zipName = "妯″瀷鏁版嵁涓虹┖锛岃鍏堣璁℃祦绋嬪畾涔夋ā鍨嬶紝鍐嶈繘琛岄儴缃诧紒";
+ zos.putNextEntry(new ZipEntry(zipName + ".txt"));
+ zos.write(zipName.getBytes(StandardCharsets.UTF_8));
+ } else {
+ String fileName = model.getName() + "-" + model.getKey();
+ // 鍘嬬缉鍖呮枃浠跺悕
+ zipName = fileName + ".zip";
+ // 灏唜ml娣诲姞鍒板帇缂╁寘涓�(鎸囧畾xml鏂囦欢鍚嶏細璇峰亣娴佺▼.bpmn20.xml
+ zos.putNextEntry(new ZipEntry(fileName + ".bpmn20.xml"));
+ zos.write(xmlBytes);
+ }
+ }
+ }
+ response.setHeader("Content-Disposition",
+ "attachment; filename=" + URLEncoder.encode(zipName, StandardCharsets.UTF_8) + ".zip");
+ response.addHeader("Access-Control-Expose-Headers", "Content-Disposition");
+ // 鍒峰嚭鍝嶅簲娴�
+ response.flushBuffer();
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ }
+
+ /**
+ * 澶嶅埗妯″瀷
+ *
+ * @param modelBo 妯″瀷鏁版嵁
+ * @return 缁撴灉
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean copyModel(ModelBo modelBo) {
+ try {
+ String key = modelBo.getKey();
+ if (StringUtils.isNotBlank(key)) {
+ // 鏌ヨ妯″瀷
+ Model model = repositoryService.createModelQuery().modelId(modelBo.getId()).singleResult();
+ if (ObjectUtil.isNotNull(model)) {
+ byte[] modelEditorSource = repositoryService.getModelEditorSource(model.getId());
+ List<Model> list = QueryUtils.modelQuery().modelKey(key).list();
+ if (CollUtil.isNotEmpty(list)) {
+ throw new ServiceException("妯″瀷KEY宸插瓨鍦紒");
+ }
+ // 鏍¢獙key鍛藉悕瑙勮寖
+ if (!Validator.isMatchRegex(FlowConstant.MODEL_KEY_PATTERN, key)) {
+ throw new ServiceException("妯″瀷鏍囪瘑KEY鍙兘瀛楃鎴栬�呬笅鍒掔嚎寮�澶达紒");
+ }
+ // 澶嶅埗妯″瀷鏁版嵁
+ Model newModel = repositoryService.newModel();
+ newModel.setKey(modelBo.getKey());
+ newModel.setName(modelBo.getName());
+ newModel.setCategory(modelBo.getCategoryCode());
+ newModel.setVersion(1);
+ newModel.setMetaInfo(modelBo.getDescription());
+ newModel.setTenantId(TenantHelper.getTenantId());
+ String xml = StrUtil.utf8Str(modelEditorSource);
+ BpmnModel bpmnModel = ModelUtils.xmlToBpmnModel(xml);
+ Process mainProcess = bpmnModel.getMainProcess();
+ mainProcess.setId(modelBo.getKey());
+ mainProcess.setName(modelBo.getName());
+ byte[] xmlBytes = new BpmnXMLConverter().convertToXML(bpmnModel);
+ repositoryService.saveModel(newModel);
+ repositoryService.addModelEditorSource(newModel.getId(), xmlBytes);
+ }
+ }
+ } catch (Exception e) {
+ throw new ServiceException(e.getMessage());
+ }
+ return true;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActProcessDefinitionServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActProcessDefinitionServiceImpl.java
new file mode 100644
index 0000000..c37e0d0
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActProcessDefinitionServiceImpl.java
@@ -0,0 +1,438 @@
+package org.dromara.workflow.service.impl;
+
+import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.codec.Base64;
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.io.FileUtil;
+import cn.hutool.core.io.IoUtil;
+import cn.hutool.core.util.ObjectUtil;
+import cn.hutool.core.util.StrUtil;
+import lombok.RequiredArgsConstructor;
+import lombok.SneakyThrows;
+import org.dromara.common.core.exception.ServiceException;
+import org.dromara.common.core.utils.StreamUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.tenant.helper.TenantHelper;
+import org.dromara.workflow.common.constant.FlowConstant;
+import org.dromara.workflow.domain.WfCategory;
+import org.dromara.workflow.domain.WfDefinitionConfig;
+import org.dromara.workflow.domain.WfNodeConfig;
+import org.dromara.workflow.domain.bo.ProcessDefinitionBo;
+import org.dromara.workflow.domain.bo.WfDefinitionConfigBo;
+import org.dromara.workflow.domain.vo.ProcessDefinitionVo;
+import org.dromara.workflow.domain.vo.WfDefinitionConfigVo;
+import org.dromara.workflow.mapper.WfDefinitionConfigMapper;
+import org.dromara.workflow.service.IActProcessDefinitionService;
+import org.dromara.workflow.service.IWfCategoryService;
+import org.dromara.workflow.service.IWfDefinitionConfigService;
+import org.dromara.workflow.service.IWfNodeConfigService;
+import org.dromara.workflow.utils.ModelUtils;
+import org.dromara.workflow.utils.QueryUtils;
+import org.flowable.bpmn.model.UserTask;
+import org.flowable.engine.ProcessMigrationService;
+import org.flowable.engine.RepositoryService;
+import org.flowable.engine.history.HistoricProcessInstance;
+import org.flowable.engine.impl.bpmn.deployer.ResourceNameUtil;
+import org.flowable.engine.repository.*;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.web.multipart.MultipartFile;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.nio.charset.StandardCharsets;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+import java.util.Set;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipInputStream;
+
+/**
+ * 娴佺▼瀹氫箟 鏈嶅姟灞傚疄鐜�
+ *
+ * @author may
+ */
+@RequiredArgsConstructor
+@Service
+public class ActProcessDefinitionServiceImpl implements IActProcessDefinitionService {
+
+ private final RepositoryService repositoryService;
+ private final ProcessMigrationService processMigrationService;
+ private final IWfCategoryService wfCategoryService;
+ private final IWfDefinitionConfigService wfDefinitionConfigService;
+ private final WfDefinitionConfigMapper wfDefinitionConfigMapper;
+ private final IWfNodeConfigService wfNodeConfigService;
+
+ /**
+ * 鍒嗛〉鏌ヨ
+ *
+ * @param bo 鍙傛暟
+ * @return 杩斿洖鍒嗛〉鍒楄〃
+ */
+ @Override
+ public TableDataInfo<ProcessDefinitionVo> page(ProcessDefinitionBo bo, PageQuery pageQuery) {
+ ProcessDefinitionQuery query = QueryUtils.definitionQuery();
+ if (StringUtils.isNotEmpty(bo.getKey())) {
+ query.processDefinitionKey(bo.getKey());
+ }
+ if (StringUtils.isNotEmpty(bo.getCategoryCode())) {
+ query.processDefinitionCategory(bo.getCategoryCode());
+ }
+ if (StringUtils.isNotEmpty(bo.getName())) {
+ query.processDefinitionNameLike("%" + bo.getName() + "%");
+ }
+ query.orderByDeploymentId().desc();
+ // 鍒嗛〉鏌ヨ
+ List<ProcessDefinitionVo> processDefinitionVoList = new ArrayList<>();
+ List<ProcessDefinition> definitionList = query.latestVersion().listPage(pageQuery.getFirstNum(), pageQuery.getPageSize());
+ List<Deployment> deploymentList = null;
+ if (CollUtil.isNotEmpty(definitionList)) {
+ List<String> deploymentIds = StreamUtils.toList(definitionList, ProcessDefinition::getDeploymentId);
+ deploymentList = QueryUtils.deploymentQuery(deploymentIds).list();
+ }
+ if (CollUtil.isNotEmpty(definitionList)) {
+ List<String> ids = StreamUtils.toList(definitionList, ProcessDefinition::getId);
+ List<WfDefinitionConfigVo> wfDefinitionConfigVos = wfDefinitionConfigService.queryList(ids);
+ for (ProcessDefinition processDefinition : definitionList) {
+ ProcessDefinitionVo processDefinitionVo = BeanUtil.toBean(processDefinition, ProcessDefinitionVo.class);
+ if (CollUtil.isNotEmpty(deploymentList)) {
+ // 閮ㄧ讲鏃堕棿
+ deploymentList.stream().filter(e -> e.getId().equals(processDefinition.getDeploymentId())).findFirst().ifPresent(e -> {
+ processDefinitionVo.setDeploymentTime(e.getDeploymentTime());
+ });
+ }
+ if (CollUtil.isNotEmpty(wfDefinitionConfigVos)) {
+ wfDefinitionConfigVos.stream().filter(e -> e.getDefinitionId().equals(processDefinition.getId())).findFirst().ifPresent(processDefinitionVo::setWfDefinitionConfigVo);
+ }
+ processDefinitionVoList.add(processDefinitionVo);
+ }
+ }
+ // 鎬昏褰曟暟
+ long total = query.count();
+ TableDataInfo<ProcessDefinitionVo> build = TableDataInfo.build();
+ build.setRows(processDefinitionVoList);
+ build.setTotal(total);
+ return build;
+ }
+
+ /**
+ * 鏌ヨ鍘嗗彶娴佺▼瀹氫箟鍒楄〃
+ *
+ * @param key 娴佺▼瀹氫箟key
+ */
+ @Override
+ public List<ProcessDefinitionVo> getListByKey(String key) {
+ List<ProcessDefinitionVo> processDefinitionVoList = new ArrayList<>();
+ ProcessDefinitionQuery query = QueryUtils.definitionQuery();
+ List<ProcessDefinition> definitionList = query.processDefinitionKey(key).list();
+ List<Deployment> deploymentList = null;
+ if (CollUtil.isNotEmpty(definitionList)) {
+ List<String> deploymentIds = StreamUtils.toList(definitionList, ProcessDefinition::getDeploymentId);
+ deploymentList = QueryUtils.deploymentQuery(deploymentIds).list();
+ }
+ if (CollUtil.isNotEmpty(definitionList)) {
+ List<String> ids = StreamUtils.toList(definitionList, ProcessDefinition::getId);
+ List<WfDefinitionConfigVo> wfDefinitionConfigVos = wfDefinitionConfigService.queryList(ids);
+ for (ProcessDefinition processDefinition : definitionList) {
+ ProcessDefinitionVo processDefinitionVo = BeanUtil.toBean(processDefinition, ProcessDefinitionVo.class);
+ if (CollUtil.isNotEmpty(deploymentList)) {
+ // 閮ㄧ讲鏃堕棿
+ deploymentList.stream().filter(e -> e.getId().equals(processDefinition.getDeploymentId())).findFirst().ifPresent(e -> {
+ processDefinitionVo.setDeploymentTime(e.getDeploymentTime());
+ });
+ if (CollUtil.isNotEmpty(wfDefinitionConfigVos)) {
+ wfDefinitionConfigVos.stream().filter(e -> e.getDefinitionId().equals(processDefinition.getId())).findFirst().ifPresent(processDefinitionVo::setWfDefinitionConfigVo);
+ }
+ }
+ processDefinitionVoList.add(processDefinitionVo);
+ }
+ }
+ return CollUtil.reverse(processDefinitionVoList);
+ }
+
+ /**
+ * 鏌ョ湅娴佺▼瀹氫箟鍥剧墖
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ @SneakyThrows
+ @Override
+ public String definitionImage(String processDefinitionId) {
+ InputStream inputStream = repositoryService.getProcessDiagram(processDefinitionId);
+ return Base64.encode(IoUtil.readBytes(inputStream));
+ }
+
+ /**
+ * 鏌ョ湅娴佺▼瀹氫箟xml鏂囦欢
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ @Override
+ public String definitionXml(String processDefinitionId) {
+ StringBuilder xml = new StringBuilder();
+ ProcessDefinition processDefinition = repositoryService.getProcessDefinition(processDefinitionId);
+ InputStream inputStream = repositoryService.getResourceAsStream(processDefinition.getDeploymentId(), processDefinition.getResourceName());
+ xml.append(IoUtil.read(inputStream, StandardCharsets.UTF_8));
+ return xml.toString();
+ }
+
+ /**
+ * 鍒犻櫎娴佺▼瀹氫箟
+ *
+ * @param deploymentIds 閮ㄧ讲id
+ * @param processDefinitionIds 娴佺▼瀹氫箟id
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean deleteDeployment(List<String> deploymentIds, List<String> processDefinitionIds) {
+ try {
+ List<HistoricProcessInstance> historicProcessInstances = QueryUtils.hisInstanceQuery().deploymentIdIn(deploymentIds).list();
+ if (CollUtil.isNotEmpty(historicProcessInstances)) {
+ Set<String> defIds = StreamUtils.toSet(historicProcessInstances, HistoricProcessInstance::getProcessDefinitionId);
+ List<ProcessDefinition> processDefinitions = QueryUtils.definitionQuery().processDefinitionIds(defIds).list();
+ if (CollUtil.isNotEmpty(processDefinitions)) {
+ Set<String> keys = StreamUtils.toSet(processDefinitions, ProcessDefinition::getKey);
+ throw new ServiceException("褰撳墠銆�" + String.join(",", keys) + "銆戞祦绋嬪畾涔夊凡琚娇鐢ㄤ笉鍙垹闄わ紒");
+ }
+ }
+ //鍒犻櫎娴佺▼瀹氫箟
+ for (String deploymentId : deploymentIds) {
+ repositoryService.deleteDeployment(deploymentId);
+ }
+ //鍒犻櫎娴佺▼瀹氫箟閰嶇疆
+ wfDefinitionConfigService.deleteByDefIds(processDefinitionIds);
+ //鍒犻櫎鑺傜偣閰嶇疆
+ wfNodeConfigService.deleteByDefIds(processDefinitionIds);
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 婵�娲绘垨鑰呮寕璧锋祦绋嬪畾涔�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ @Override
+ public boolean updateDefinitionState(String processDefinitionId) {
+ try {
+ ProcessDefinition processDefinition = QueryUtils.definitionQuery()
+ .processDefinitionId(processDefinitionId).singleResult();
+ //灏嗗綋鍓嶄负鎸傝捣鐘舵�佹洿鏂颁负婵�娲荤姸鎬�
+ //鍙傛暟璇存槑锛氬弬鏁�1锛氭祦绋嬪畾涔塱d,鍙傛暟2锛氭槸鍚︽縺娲伙紙true鏄惁绾ц仈瀵瑰簲娴佺▼瀹炰緥锛屾縺娲讳簡鍒欏搴旀祦绋嬪疄渚嬮兘鍙互瀹℃壒锛夛紝
+ //鍙傛暟3锛氫粈涔堟椂鍊欐縺娲伙紝濡傛灉涓簄ull鍒欑珛鍗虫縺娲伙紝濡傛灉涓哄叿浣撴椂闂村垯鍒拌揪姝ゆ椂闂村悗婵�娲�
+ if (processDefinition.isSuspended()) {
+ repositoryService.activateProcessDefinitionById(processDefinitionId, true, null);
+ } else {
+ repositoryService.suspendProcessDefinitionById(processDefinitionId, true, null);
+ }
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException("鎿嶄綔澶辫触:" + e.getMessage());
+ }
+ }
+
+ /**
+ * 杩佺Щ娴佺▼瀹氫箟
+ *
+ * @param currentProcessDefinitionId 褰撳墠娴佺▼瀹氫箟id
+ * @param fromProcessDefinitionId 闇�瑕佽縼绉诲埌鐨勬祦绋嬪畾涔塱d
+ */
+
+ @Override
+ public boolean migrationDefinition(String currentProcessDefinitionId, String fromProcessDefinitionId) {
+ try {
+ // 杩佺Щ楠岃瘉
+ boolean migrationValid = processMigrationService.createProcessInstanceMigrationBuilder()
+ .migrateToProcessDefinition(currentProcessDefinitionId)
+ .validateMigrationOfProcessInstances(fromProcessDefinitionId)
+ .isMigrationValid();
+ if (!migrationValid) {
+ throw new ServiceException("娴佺▼瀹氫箟宸紓杩囧ぇ鏃犳硶杩佺Щ锛岃淇敼娴佺▼鍥�");
+ }
+ // 宸茬粨鏉熺殑娴佺▼瀹炰緥涓嶄細杩佺Щ
+ processMigrationService.createProcessInstanceMigrationBuilder()
+ .migrateToProcessDefinition(currentProcessDefinitionId)
+ .migrateProcessInstances(fromProcessDefinitionId);
+ return true;
+ } catch (Exception e) {
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 娴佺▼瀹氫箟杞崲涓烘ā鍨�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ @Override
+ public boolean convertToModel(String processDefinitionId) {
+ ProcessDefinition pd = QueryUtils.definitionQuery()
+ .processDefinitionId(processDefinitionId).singleResult();
+ InputStream inputStream = repositoryService.getResourceAsStream(pd.getDeploymentId(), pd.getResourceName());
+ ModelQuery query = QueryUtils.modelQuery();
+ Model model = query.modelKey(pd.getKey()).singleResult();
+ try {
+ if (ObjectUtil.isNotNull(model)) {
+ repositoryService.addModelEditorSource(model.getId(), IoUtil.readBytes(inputStream));
+ } else {
+ Model modelData = repositoryService.newModel();
+ modelData.setKey(pd.getKey());
+ modelData.setName(pd.getName());
+ modelData.setTenantId(pd.getTenantId());
+ repositoryService.saveModel(modelData);
+ repositoryService.addModelEditorSource(modelData.getId(), IoUtil.readBytes(inputStream));
+ }
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 閫氳繃zip鎴杧ml閮ㄧ讲娴佺▼瀹氫箟
+ *
+ * @param file 鏂囦欢
+ * @param categoryCode 鍒嗙被
+ */
+ @SneakyThrows
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public void deployByFile(MultipartFile file, String categoryCode) {
+
+ WfCategory wfCategory = wfCategoryService.queryByCategoryCode(categoryCode);
+ if (wfCategory == null) {
+ throw new ServiceException("娴佺▼鍒嗙被涓嶅瓨鍦�");
+ }
+ // 鏂囦欢鍚庣紑鍚�
+ String suffix = FileUtil.extName(file.getOriginalFilename());
+ InputStream inputStream = file.getInputStream();
+ if (FlowConstant.ZIP.equalsIgnoreCase(suffix)) {
+ ZipInputStream zipInputStream = null;
+ try {
+ zipInputStream = new ZipInputStream(inputStream);
+ ZipEntry zipEntry;
+ while ((zipEntry = zipInputStream.getNextEntry()) != null) {
+ String filename = zipEntry.getName();
+ String[] splitFilename = filename.substring(0, filename.lastIndexOf(".")).split("-");
+ //娴佺▼鍚嶇О
+ String processName = splitFilename[0];
+ //娴佺▼key
+ String processKey = splitFilename[1];
+ ProcessDefinition oldProcessDefinition = QueryUtils.definitionQuery().processDefinitionKey(processKey).latestVersion().singleResult();
+ DeploymentBuilder builder = repositoryService.createDeployment();
+ Deployment deployment = builder.addInputStream(filename, zipInputStream)
+ .tenantId(TenantHelper.getTenantId())
+ .name(processName).key(processKey).category(categoryCode).deploy();
+ ProcessDefinition definition = QueryUtils.definitionQuery().deploymentId(deployment.getId()).singleResult();
+ repositoryService.setProcessDefinitionCategory(definition.getId(), categoryCode);
+ setWfConfig(oldProcessDefinition, definition);
+ zipInputStream.closeEntry();
+ }
+ } catch (IOException e) {
+ throw new RuntimeException(e);
+ } finally {
+ if (zipInputStream != null) {
+ zipInputStream.close();
+ }
+ }
+ //鍒濆鍖栭厤缃暟鎹紙demo浣跨敤锛屼笉鐢ㄥ彲鍒犻櫎锛�
+ initWfDefConfig();
+ } else {
+ String originalFilename = file.getOriginalFilename();
+ String bpmnResourceSuffix = ResourceNameUtil.BPMN_RESOURCE_SUFFIXES[0];
+ if (originalFilename.contains(bpmnResourceSuffix)) {
+ // 鏂囦欢鍚� = 娴佺▼鍚嶇О-娴佺▼key
+ String[] splitFilename = originalFilename.substring(0, originalFilename.lastIndexOf(".")).split("-");
+ if (splitFilename.length < 2) {
+ throw new ServiceException("鏂囦欢鍚� = 娴佺▼鍚嶇О-娴佺▼KEY");
+ }
+ //娴佺▼鍚嶇О
+ String processName = splitFilename[0];
+ //娴佺▼key
+ String processKey = splitFilename[1];
+ ProcessDefinition oldProcessDefinition = QueryUtils.definitionQuery().processDefinitionKey(processKey).latestVersion().singleResult();
+ DeploymentBuilder builder = repositoryService.createDeployment();
+ Deployment deployment = builder.addInputStream(originalFilename, inputStream)
+ .tenantId(TenantHelper.getTenantId())
+ .name(processName).key(processKey).category(categoryCode).deploy();
+ // 鏇存柊鍒嗙被
+ ProcessDefinition definition = QueryUtils.definitionQuery().deploymentId(deployment.getId()).singleResult();
+ repositoryService.setProcessDefinitionCategory(definition.getId(), categoryCode);
+ setWfConfig(oldProcessDefinition, definition);
+ } else {
+ throw new ServiceException("鏂囦欢绫诲瀷涓婁紶閿欒锛�");
+ }
+ }
+
+ }
+
+ /**
+ * 鍒濆鍖栭厤缃暟鎹紙demo浣跨敤锛屼笉鐢ㄥ彲鍒犻櫎锛�
+ */
+ private void initWfDefConfig() {
+ List<WfDefinitionConfig> wfDefinitionConfigs = wfDefinitionConfigMapper.selectList();
+ if (CollUtil.isEmpty(wfDefinitionConfigs)) {
+ ProcessDefinition processDefinition = QueryUtils.definitionQuery().processDefinitionKey("leave1").latestVersion().singleResult();
+ if (processDefinition != null) {
+ WfDefinitionConfigBo wfDefinitionConfigBo = new WfDefinitionConfigBo();
+ wfDefinitionConfigBo.setDefinitionId(processDefinition.getId());
+ wfDefinitionConfigBo.setProcessKey(processDefinition.getKey());
+ wfDefinitionConfigBo.setTableName("test_leave");
+ wfDefinitionConfigBo.setVersion(processDefinition.getVersion());
+ wfDefinitionConfigService.saveOrUpdate(wfDefinitionConfigBo);
+ }
+ }
+
+ }
+
+ /**
+ * 璁剧疆琛ㄥ崟鍐呭
+ *
+ * @param oldProcessDefinition 閮ㄧ讲鍓嶆渶鏂版祦绋嬪畾涔�
+ * @param definition 閮ㄧ讲鍚庢渶鏂版祦绋嬪畾涔�
+ */
+ private void setWfConfig(ProcessDefinition oldProcessDefinition, ProcessDefinition definition) {
+ //鏇存柊娴佺▼瀹氫箟琛ㄥ崟
+ if (oldProcessDefinition != null) {
+ WfDefinitionConfigVo definitionVo = wfDefinitionConfigService.getByDefId(oldProcessDefinition.getId());
+ if (definitionVo != null) {
+ wfDefinitionConfigService.deleteByDefIds(Collections.singletonList(oldProcessDefinition.getId()));
+ WfDefinitionConfigBo wfDefinitionConfigBo = new WfDefinitionConfigBo();
+ wfDefinitionConfigBo.setDefinitionId(definition.getId());
+ wfDefinitionConfigBo.setProcessKey(definition.getKey());
+ wfDefinitionConfigBo.setTableName(definitionVo.getTableName());
+ wfDefinitionConfigBo.setVersion(definition.getVersion());
+ wfDefinitionConfigBo.setRemark(definitionVo.getRemark());
+ wfDefinitionConfigService.saveOrUpdate(wfDefinitionConfigBo);
+ }
+ }
+ //鏇存柊娴佺▼鑺傜偣閰嶇疆琛ㄥ崟
+ List<UserTask> userTasks = ModelUtils.getUserTaskFlowElements(definition.getId());
+ UserTask applyUserTask = ModelUtils.getApplyUserTask(definition.getId());
+ List<WfNodeConfig> wfNodeConfigList = new ArrayList<>();
+ for (UserTask userTask : userTasks) {
+ if (StringUtils.isNotBlank(userTask.getFormKey()) && userTask.getFormKey().contains(StrUtil.COLON)) {
+ WfNodeConfig wfNodeConfig = new WfNodeConfig();
+ wfNodeConfig.setNodeId(userTask.getId());
+ wfNodeConfig.setNodeName(userTask.getName());
+ wfNodeConfig.setDefinitionId(definition.getId());
+ String[] split = userTask.getFormKey().split(StrUtil.COLON);
+ wfNodeConfig.setFormType(split[0]);
+ wfNodeConfig.setFormId(Long.valueOf(split[1]));
+ wfNodeConfig.setApplyUserTask(applyUserTask.getId().equals(userTask.getId()) ? FlowConstant.TRUE : FlowConstant.FALSE);
+ wfNodeConfigList.add(wfNodeConfig);
+ }
+ }
+ if (CollUtil.isNotEmpty(wfNodeConfigList)) {
+ wfNodeConfigService.saveOrUpdate(wfNodeConfigList);
+ }
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActProcessInstanceServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActProcessInstanceServiceImpl.java
new file mode 100644
index 0000000..b64c79e
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActProcessInstanceServiceImpl.java
@@ -0,0 +1,683 @@
+package org.dromara.workflow.service.impl;
+
+import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.codec.Base64;
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.convert.Convert;
+import cn.hutool.core.io.IoUtil;
+import cn.hutool.core.util.ObjectUtil;
+import lombok.RequiredArgsConstructor;
+import lombok.SneakyThrows;
+import lombok.extern.slf4j.Slf4j;
+import org.dromara.common.core.exception.ServiceException;
+import org.dromara.common.core.utils.StreamUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.satoken.utils.LoginHelper;
+import org.dromara.workflow.common.constant.FlowConstant;
+import org.dromara.workflow.common.enums.BusinessStatusEnum;
+import org.dromara.workflow.common.enums.TaskStatusEnum;
+import org.dromara.workflow.domain.ActHiProcinst;
+import org.dromara.workflow.domain.bo.ProcessInstanceBo;
+import org.dromara.workflow.domain.bo.ProcessInvalidBo;
+import org.dromara.workflow.domain.bo.TaskUrgingBo;
+import org.dromara.workflow.domain.vo.*;
+import org.dromara.workflow.flowable.CustomDefaultProcessDiagramGenerator;
+import org.dromara.workflow.flowable.cmd.DeleteExecutionCmd;
+import org.dromara.workflow.flowable.cmd.ExecutionChildByExecutionIdCmd;
+import org.dromara.workflow.flowable.strategy.FlowEventStrategy;
+import org.dromara.workflow.flowable.strategy.FlowProcessEventHandler;
+import org.dromara.workflow.service.IActHiProcinstService;
+import org.dromara.workflow.service.IActProcessInstanceService;
+import org.dromara.workflow.service.IWfNodeConfigService;
+import org.dromara.workflow.service.IWfTaskBackNodeService;
+import org.dromara.workflow.utils.QueryUtils;
+import org.dromara.workflow.utils.WorkflowUtils;
+import org.flowable.bpmn.model.*;
+import org.flowable.engine.*;
+import org.flowable.engine.history.HistoricActivityInstance;
+import org.flowable.engine.history.HistoricProcessInstance;
+import org.flowable.engine.history.HistoricProcessInstanceQuery;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntity;
+import org.flowable.engine.repository.ProcessDefinition;
+import org.flowable.engine.runtime.ProcessInstance;
+import org.flowable.engine.runtime.ProcessInstanceQuery;
+import org.flowable.engine.task.Attachment;
+import org.flowable.engine.task.Comment;
+import org.flowable.task.api.Task;
+import org.flowable.task.api.history.HistoricTaskInstance;
+import org.springframework.beans.BeanUtils;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.awt.*;
+import java.io.InputStream;
+import java.nio.charset.StandardCharsets;
+import java.util.List;
+import java.util.*;
+import java.util.stream.Collectors;
+
+/**
+ * 娴佺▼瀹炰緥 鏈嶅姟灞傚疄鐜�
+ *
+ * @author may
+ */
+@Slf4j
+@RequiredArgsConstructor
+@Service
+public class ActProcessInstanceServiceImpl implements IActProcessInstanceService {
+
+ private final RepositoryService repositoryService;
+ private final RuntimeService runtimeService;
+ private final HistoryService historyService;
+ private final TaskService taskService;
+ private final IActHiProcinstService actHiProcinstService;
+ private final ManagementService managementService;
+ private final FlowEventStrategy flowEventStrategy;
+ private final IWfTaskBackNodeService wfTaskBackNodeService;
+ private final IWfNodeConfigService wfNodeConfigService;
+
+ @Value("${flowable.activity-font-name}")
+ private String activityFontName;
+
+ @Value("${flowable.label-font-name}")
+ private String labelFontName;
+
+ @Value("${flowable.annotation-font-name}")
+ private String annotationFontName;
+
+ /**
+ * 鍒嗛〉鏌ヨ姝e湪杩愯鐨勬祦绋嬪疄渚�
+ *
+ * @param bo 鍙傛暟
+ */
+ @Override
+ public TableDataInfo<ProcessInstanceVo> getPageByRunning(ProcessInstanceBo bo, PageQuery pageQuery) {
+ List<ProcessInstanceVo> list = new ArrayList<>();
+ ProcessInstanceQuery query = QueryUtils.instanceQuery();
+ if (StringUtils.isNotBlank(bo.getName())) {
+ query.processInstanceNameLikeIgnoreCase("%" + bo.getName() + "%");
+ }
+ if (StringUtils.isNotBlank(bo.getKey())) {
+ query.processDefinitionKey(bo.getKey());
+ }
+ if (StringUtils.isNotBlank(bo.getStartUserId())) {
+ query.startedBy(bo.getStartUserId());
+ }
+ if (StringUtils.isNotBlank(bo.getBusinessKey())) {
+ query.processInstanceBusinessKey(bo.getBusinessKey());
+ }
+ if (StringUtils.isNotBlank(bo.getCategoryCode())) {
+ query.processDefinitionCategory(bo.getCategoryCode());
+ }
+ query.orderByStartTime().desc();
+ List<ProcessInstance> processInstances = query.listPage(pageQuery.getFirstNum(), pageQuery.getPageSize());
+ for (ProcessInstance processInstance : processInstances) {
+ ProcessInstanceVo processInstanceVo = BeanUtil.toBean(processInstance, ProcessInstanceVo.class);
+ processInstanceVo.setIsSuspended(processInstance.isSuspended());
+ processInstanceVo.setBusinessStatusName(BusinessStatusEnum.findByStatus(processInstance.getBusinessStatus()));
+ list.add(processInstanceVo);
+ }
+ if (CollUtil.isNotEmpty(list)) {
+ List<String> processDefinitionIds = StreamUtils.toList(list, ProcessInstanceVo::getProcessDefinitionId);
+ List<WfNodeConfigVo> wfNodeConfigVoList = wfNodeConfigService.selectByDefIds(processDefinitionIds);
+ for (ProcessInstanceVo processInstanceVo : list) {
+ if (CollUtil.isNotEmpty(wfNodeConfigVoList)) {
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(processInstanceVo.getProcessDefinitionId()) && FlowConstant.TRUE.equals(e.getApplyUserTask())).findFirst().ifPresent(processInstanceVo::setWfNodeConfigVo);
+ }
+ }
+ }
+ long count = query.count();
+ TableDataInfo<ProcessInstanceVo> build = TableDataInfo.build();
+ build.setRows(list);
+ build.setTotal(count);
+ return build;
+ }
+
+ /**
+ * 鍒嗛〉鏌ヨ宸茬粨鏉熺殑娴佺▼瀹炰緥
+ *
+ * @param bo 鍙傛暟
+ */
+ @Override
+ public TableDataInfo<ProcessInstanceVo> getPageByFinish(ProcessInstanceBo bo, PageQuery pageQuery) {
+ List<ProcessInstanceVo> list = new ArrayList<>();
+ HistoricProcessInstanceQuery query = QueryUtils.hisInstanceQuery()
+ .finished().orderByProcessInstanceEndTime().desc();
+ if (StringUtils.isNotEmpty(bo.getName())) {
+ query.processInstanceNameLikeIgnoreCase("%" + bo.getName() + "%");
+ }
+ if (StringUtils.isNotBlank(bo.getKey())) {
+ query.processDefinitionKey(bo.getKey());
+ }
+ if (StringUtils.isNotEmpty(bo.getStartUserId())) {
+ query.startedBy(bo.getStartUserId());
+ }
+ if (StringUtils.isNotBlank(bo.getBusinessKey())) {
+ query.processInstanceBusinessKey(bo.getBusinessKey());
+ }
+ if (StringUtils.isNotBlank(bo.getCategoryCode())) {
+ query.processDefinitionCategory(bo.getCategoryCode());
+ }
+ List<HistoricProcessInstance> historicProcessInstances = query.listPage(pageQuery.getFirstNum(), pageQuery.getPageSize());
+ for (HistoricProcessInstance historicProcessInstance : historicProcessInstances) {
+ ProcessInstanceVo processInstanceVo = BeanUtil.toBean(historicProcessInstance, ProcessInstanceVo.class);
+ processInstanceVo.setBusinessStatusName(BusinessStatusEnum.findByStatus(historicProcessInstance.getBusinessStatus()));
+ list.add(processInstanceVo);
+ }
+ if (CollUtil.isNotEmpty(list)) {
+ List<String> processDefinitionIds = StreamUtils.toList(list, ProcessInstanceVo::getProcessDefinitionId);
+ List<WfNodeConfigVo> wfNodeConfigVoList = wfNodeConfigService.selectByDefIds(processDefinitionIds);
+ for (ProcessInstanceVo processInstanceVo : list) {
+ if (CollUtil.isNotEmpty(wfNodeConfigVoList)) {
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(processInstanceVo.getProcessDefinitionId()) && FlowConstant.TRUE.equals(e.getApplyUserTask())).findFirst().ifPresent(processInstanceVo::setWfNodeConfigVo);
+ }
+ }
+ }
+ long count = query.count();
+ TableDataInfo<ProcessInstanceVo> build = TableDataInfo.build();
+ build.setRows(list);
+ build.setTotal(count);
+ return build;
+ }
+
+ /**
+ * 閫氳繃娴佺▼瀹炰緥id鑾峰彇鍘嗗彶娴佺▼鍥�
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ @SneakyThrows
+ @Override
+ public String getHistoryImage(String processInstanceId) {
+ String processDefinitionId;
+ // 鑾峰彇褰撳墠鐨勬祦绋嬪疄渚�
+ ProcessInstance processInstance = QueryUtils.instanceQuery(processInstanceId).singleResult();
+ // 濡傛灉娴佺▼宸茬粡缁撴潫锛屽垯寰楀埌缁撴潫鑺傜偣
+ if (Objects.isNull(processInstance)) {
+ HistoricProcessInstance pi = QueryUtils.hisInstanceQuery(processInstanceId).singleResult();
+ processDefinitionId = pi.getProcessDefinitionId();
+ } else {
+ // 鏍规嵁娴佺▼瀹炰緥ID鑾峰緱褰撳墠澶勪簬娲诲姩鐘舵�佺殑ActivityId鍚堥泦
+ ProcessInstance pi = QueryUtils.instanceQuery(processInstanceId).singleResult();
+ processDefinitionId = pi.getProcessDefinitionId();
+ }
+
+ // 鑾峰緱娲诲姩鐨勮妭鐐�
+ List<HistoricActivityInstance> highLightedFlowList = QueryUtils.hisActivityInstanceQuery(processInstanceId).orderByHistoricActivityInstanceStartTime().asc().list();
+
+ List<String> highLightedFlows = new ArrayList<>();
+ List<String> highLightedNodes = new ArrayList<>();
+ //楂樹寒
+ for (HistoricActivityInstance tempActivity : highLightedFlowList) {
+ if (FlowConstant.SEQUENCE_FLOW.equals(tempActivity.getActivityType())) {
+ //楂樹寒绾�
+ highLightedFlows.add(tempActivity.getActivityId());
+ } else {
+ //楂樹寒鑺傜偣
+ if (tempActivity.getEndTime() == null) {
+ highLightedNodes.add(Color.RED.toString() + tempActivity.getActivityId());
+ } else {
+ highLightedNodes.add(tempActivity.getActivityId());
+ }
+ }
+ }
+ List<String> highLightedNodeList = new ArrayList<>();
+ //杩愯涓殑鑺傜偣
+ List<String> redNodeCollect = StreamUtils.filter(highLightedNodes, e -> e.contains(Color.RED.toString()));
+ //鎺掗櫎涓庤繍琛屼腑鐩稿悓鐨勮妭鐐�
+ for (String nodeId : highLightedNodes) {
+ if (!nodeId.contains(Color.RED.toString()) && !redNodeCollect.contains(Color.RED + nodeId)) {
+ highLightedNodeList.add(nodeId);
+ }
+ }
+ highLightedNodeList.addAll(redNodeCollect);
+ BpmnModel bpmnModel = repositoryService.getBpmnModel(processDefinitionId);
+ CustomDefaultProcessDiagramGenerator diagramGenerator = new CustomDefaultProcessDiagramGenerator();
+ InputStream inputStream = diagramGenerator.generateDiagram(bpmnModel, "png", highLightedNodeList, highLightedFlows, activityFontName, labelFontName, annotationFontName, null, 1.0, true);
+ return Base64.encode(IoUtil.readBytes(inputStream));
+ }
+
+ /**
+ * 閫氳繃娴佺▼瀹炰緥id鑾峰彇鍘嗗彶娴佺▼鍥捐繍琛屼腑锛屽巻鍙茬瓑鑺傜偣
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ @Override
+ public Map<String, Object> getHistoryList(String processInstanceId) {
+ Map<String, Object> map = new HashMap<>();
+ List<Map<String, Object>> taskList = new ArrayList<>();
+ HistoricProcessInstance historicProcessInstance = QueryUtils.hisInstanceQuery(processInstanceId).singleResult();
+ StringBuilder xml = new StringBuilder();
+ ProcessDefinition processDefinition = repositoryService.getProcessDefinition(historicProcessInstance.getProcessDefinitionId());
+ // 鑾峰彇鑺傜偣
+ List<HistoricActivityInstance> highLightedFlowList = QueryUtils.hisActivityInstanceQuery(processInstanceId).orderByHistoricActivityInstanceStartTime().asc().list();
+ for (HistoricActivityInstance tempActivity : highLightedFlowList) {
+ Map<String, Object> task = new HashMap<>();
+ if (!FlowConstant.SEQUENCE_FLOW.equals(tempActivity.getActivityType()) &&
+ !FlowConstant.PARALLEL_GATEWAY.equals(tempActivity.getActivityType()) &&
+ !FlowConstant.EXCLUSIVE_GATEWAY.equals(tempActivity.getActivityType()) &&
+ !FlowConstant.INCLUSIVE_GATEWAY.equals(tempActivity.getActivityType())
+ ) {
+ task.put("key", tempActivity.getActivityId());
+ task.put("completed", tempActivity.getEndTime() != null);
+ task.put("activityType", tempActivity.getActivityType());
+ taskList.add(task);
+ }
+ }
+ ProcessInstance processInstance = QueryUtils.instanceQuery(processInstanceId).singleResult();
+ if (processInstance != null) {
+ taskList = taskList.stream().filter(e -> !e.get("activityType").equals(FlowConstant.END_EVENT)).collect(Collectors.toList());
+ }
+ //鏌ヨ鍑鸿繍琛屼腑鑺傜偣
+ List<Map<String, Object>> runtimeNodeList = taskList.stream().filter(e -> !(Boolean) e.get("completed")).collect(Collectors.toList());
+ if (CollUtil.isNotEmpty(runtimeNodeList)) {
+ Iterator<Map<String, Object>> iterator = taskList.iterator();
+ while (iterator.hasNext()) {
+ Map<String, Object> next = iterator.next();
+ runtimeNodeList.stream().filter(t -> t.get("key").equals(next.get("key")) && (Boolean) next.get("completed")).findFirst().ifPresent(t -> iterator.remove());
+ }
+ }
+ map.put("taskList", taskList);
+ List<ActHistoryInfoVo> historyTaskList = getHistoryTaskList(processInstanceId);
+ map.put("historyList", historyTaskList);
+ InputStream inputStream = repositoryService.getResourceAsStream(processDefinition.getDeploymentId(), processDefinition.getResourceName());
+ xml.append(IoUtil.read(inputStream, StandardCharsets.UTF_8));
+ map.put("xml", xml.toString());
+ return map;
+ }
+
+ /**
+ * 鑾峰彇鍘嗗彶浠诲姟鑺傜偣淇℃伅
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ private List<ActHistoryInfoVo> getHistoryTaskList(String processInstanceId) {
+ //鏌ヨ浠诲姟鍔炵悊璁板綍
+ List<HistoricTaskInstance> list = QueryUtils.hisTaskInstanceQuery(processInstanceId).orderByHistoricTaskInstanceEndTime().desc().list();
+ list = StreamUtils.sorted(list, Comparator.comparing(HistoricTaskInstance::getEndTime, Comparator.nullsFirst(Date::compareTo)).reversed());
+ List<ActHistoryInfoVo> actHistoryInfoVoList = new ArrayList<>();
+ for (HistoricTaskInstance historicTaskInstance : list) {
+ ActHistoryInfoVo actHistoryInfoVo = new ActHistoryInfoVo();
+ BeanUtils.copyProperties(historicTaskInstance, actHistoryInfoVo);
+ actHistoryInfoVo.setStatus(actHistoryInfoVo.getEndTime() == null ? "寰呭鐞�" : "宸插鐞�");
+ if (ObjectUtil.isNotEmpty(historicTaskInstance.getDurationInMillis())) {
+ actHistoryInfoVo.setRunDuration(getDuration(historicTaskInstance.getDurationInMillis()));
+ }
+ actHistoryInfoVoList.add(actHistoryInfoVo);
+ }
+ List<ActHistoryInfoVo> historyInfoVoList = new ArrayList<>();
+ Map<String, List<ActHistoryInfoVo>> groupByKey = StreamUtils.groupByKey(actHistoryInfoVoList, ActHistoryInfoVo::getTaskDefinitionKey);
+ for (Map.Entry<String, List<ActHistoryInfoVo>> entry : groupByKey.entrySet()) {
+ ActHistoryInfoVo historyInfoVo = new ActHistoryInfoVo();
+ BeanUtils.copyProperties(entry.getValue().get(0), historyInfoVo);
+ actHistoryInfoVoList.stream().filter(e -> e.getTaskDefinitionKey().equals(entry.getKey()) && e.getEndTime() == null).findFirst()
+ .ifPresent(e -> {
+ historyInfoVo.setStatus("寰呭鐞�");
+ historyInfoVo.setStartTime(e.getStartTime());
+ historyInfoVo.setEndTime(null);
+ historyInfoVo.setRunDuration(null);
+ if (ObjectUtil.isEmpty(e.getAssignee())) {
+ ParticipantVo participantVo = WorkflowUtils.getCurrentTaskParticipant(e.getId());
+ if (ObjectUtil.isNotEmpty(participantVo) && CollUtil.isNotEmpty(participantVo.getCandidate())) {
+ historyInfoVo.setAssignee(StreamUtils.join(participantVo.getCandidate(), Convert::toStr));
+ }
+ }
+ });
+ historyInfoVoList.add(historyInfoVo);
+ }
+ return historyInfoVoList;
+ }
+
+ /**
+ * 鑾峰彇瀹℃壒璁板綍
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ @Override
+ public List<ActHistoryInfoVo> getHistoryRecord(String processInstanceId) {
+ // 鏌ヨ浠诲姟鍔炵悊璁板綍
+ List<HistoricTaskInstance> list = QueryUtils.hisTaskInstanceQuery(processInstanceId).orderByHistoricTaskInstanceEndTime().desc().list();
+ list = StreamUtils.sorted(list, Comparator.comparing(HistoricTaskInstance::getEndTime, Comparator.nullsFirst(Date::compareTo)).reversed());
+ List<ActHistoryInfoVo> actHistoryInfoVoList = new ArrayList<>();
+ List<Comment> processInstanceComments = taskService.getProcessInstanceComments(processInstanceId);
+ //闄勪欢
+ List<Attachment> attachmentList = taskService.getProcessInstanceAttachments(processInstanceId);
+ for (HistoricTaskInstance historicTaskInstance : list) {
+ ActHistoryInfoVo actHistoryInfoVo = new ActHistoryInfoVo();
+ BeanUtils.copyProperties(historicTaskInstance, actHistoryInfoVo);
+ if (actHistoryInfoVo.getEndTime() == null) {
+ actHistoryInfoVo.setStatus(TaskStatusEnum.WAITING.getStatus());
+ actHistoryInfoVo.setStatusName(TaskStatusEnum.WAITING.getDesc());
+ }
+ if (CollUtil.isNotEmpty(processInstanceComments)) {
+ processInstanceComments.stream().filter(e -> e.getTaskId().equals(historicTaskInstance.getId())).findFirst().ifPresent(e -> {
+ actHistoryInfoVo.setComment(e.getFullMessage());
+ actHistoryInfoVo.setStatus(e.getType());
+ actHistoryInfoVo.setStatusName(TaskStatusEnum.findByStatus(e.getType()));
+ });
+ }
+ if (ObjectUtil.isNotEmpty(historicTaskInstance.getDurationInMillis())) {
+ actHistoryInfoVo.setRunDuration(getDuration(historicTaskInstance.getDurationInMillis()));
+ }
+ //闄勪欢
+ if (CollUtil.isNotEmpty(attachmentList)) {
+ List<Attachment> attachments = attachmentList.stream().filter(e -> e.getTaskId().equals(historicTaskInstance.getId())).collect(Collectors.toList());
+ if (CollUtil.isNotEmpty(attachments)) {
+ actHistoryInfoVo.setAttachmentList(attachments);
+ }
+ }
+ //璁剧疆浜哄憳id
+ if (ObjectUtil.isEmpty(historicTaskInstance.getAssignee())) {
+ ParticipantVo participantVo = WorkflowUtils.getCurrentTaskParticipant(historicTaskInstance.getId());
+ if (ObjectUtil.isNotEmpty(participantVo) && CollUtil.isNotEmpty(participantVo.getCandidate())) {
+ actHistoryInfoVo.setAssignee(StreamUtils.join(participantVo.getCandidate(), Convert::toStr));
+ }
+ }
+ actHistoryInfoVoList.add(actHistoryInfoVo);
+ }
+ // 瀹℃壒璁板綍
+ Map<String, List<ActHistoryInfoVo>> groupByKey = StreamUtils.groupByKey(actHistoryInfoVoList, ActHistoryInfoVo::getTaskDefinitionKey);
+ for (Map.Entry<String, List<ActHistoryInfoVo>> entry : groupByKey.entrySet()) {
+ ActHistoryInfoVo actHistoryInfoVo = BeanUtil.toBean(entry.getValue().get(0), ActHistoryInfoVo.class);
+ actHistoryInfoVoList.stream().filter(e -> e.getTaskDefinitionKey().equals(entry.getKey()) && e.getEndTime() != null).findFirst()
+ .ifPresent(e -> {
+ actHistoryInfoVo.setStatus("宸插鐞�");
+ actHistoryInfoVo.setStartTime(e.getStartTime());
+ });
+ actHistoryInfoVoList.stream().filter(e -> e.getTaskDefinitionKey().equals(entry.getKey()) && e.getEndTime() == null).findFirst()
+ .ifPresent(e -> {
+ actHistoryInfoVo.setStatus("寰呭鐞�");
+ actHistoryInfoVo.setStartTime(e.getStartTime());
+ actHistoryInfoVo.setEndTime(null);
+ actHistoryInfoVo.setRunDuration(null);
+ });
+ }
+ List<ActHistoryInfoVo> recordList = new ArrayList<>();
+ // 寰呭姙鐞�
+ recordList.addAll(StreamUtils.filter(actHistoryInfoVoList, e -> e.getEndTime() == null));
+ // 宸插姙鐞�
+ recordList.addAll(StreamUtils.filter(actHistoryInfoVoList, e -> e.getEndTime() != null));
+
+ return recordList;
+ }
+
+ /**
+ * 浠诲姟瀹屾垚鏃堕棿澶勭悊
+ *
+ * @param time 鏃堕棿
+ */
+ private String getDuration(long time) {
+
+ long day = time / (24 * 60 * 60 * 1000);
+ long hour = (time / (60 * 60 * 1000) - day * 24);
+ long minute = ((time / (60 * 1000)) - day * 24 * 60 - hour * 60);
+ long second = (time / 1000 - day * 24 * 60 * 60 - hour * 60 * 60 - minute * 60);
+
+ if (day > 0) {
+ return day + "澶�" + hour + "灏忔椂" + minute + "鍒嗛挓";
+ }
+ if (hour > 0) {
+ return hour + "灏忔椂" + minute + "鍒嗛挓";
+ }
+ if (minute > 0) {
+ return minute + "鍒嗛挓";
+ }
+ if (second > 0) {
+ return second + "绉�";
+ } else {
+ return 0 + "绉�";
+ }
+ }
+
+ /**
+ * 浣滃簾娴佺▼瀹炰緥锛屼笉浼氬垹闄ゅ巻鍙茶褰�(鍒犻櫎杩愯涓殑瀹炰緥)
+ *
+ * @param processInvalidBo 鍙傛暟
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean deleteRunInstance(ProcessInvalidBo processInvalidBo) {
+ try {
+ List<Task> list = QueryUtils.taskQuery(processInvalidBo.getProcessInstanceId()).list();
+ List<Task> subTasks = StreamUtils.filter(list, e -> StringUtils.isNotBlank(e.getParentTaskId()));
+ if (CollUtil.isNotEmpty(subTasks)) {
+ subTasks.forEach(e -> taskService.deleteTask(e.getId()));
+ }
+ String deleteReason = LoginHelper.getLoginUser().getNickname() + "浣滃簾浜嗗綋鍓嶇敵璇凤紒";
+ if (StringUtils.isNotBlank(processInvalidBo.getDeleteReason())) {
+ deleteReason = LoginHelper.getLoginUser().getNickname() + "浣滃簾鐞嗙敱:" + processInvalidBo.getDeleteReason();
+ }
+ for (Task task : StreamUtils.filter(list, e -> StringUtils.isBlank(e.getParentTaskId()))) {
+ taskService.addComment(task.getId(), task.getProcessInstanceId(), TaskStatusEnum.INVALID.getStatus(), deleteReason);
+ }
+ HistoricProcessInstance historicProcessInstance = QueryUtils.hisInstanceQuery(processInvalidBo.getProcessInstanceId()).singleResult();
+ BusinessStatusEnum.checkInvalidStatus(historicProcessInstance.getBusinessStatus());
+ runtimeService.updateBusinessStatus(processInvalidBo.getProcessInstanceId(), BusinessStatusEnum.INVALID.getStatus());
+ runtimeService.deleteProcessInstance(processInvalidBo.getProcessInstanceId(), deleteReason);
+ FlowProcessEventHandler processHandler = flowEventStrategy.getProcessHandler(historicProcessInstance.getProcessDefinitionKey());
+ if (processHandler != null) {
+ processHandler.handleProcess(historicProcessInstance.getBusinessKey(), BusinessStatusEnum.INVALID.getStatus(), false);
+ }
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 杩愯涓殑瀹炰緥 鍒犻櫎绋嬪疄渚嬶紝鍒犻櫎鍘嗗彶璁板綍锛屽垹闄や笟鍔′笌娴佺▼鍏宠仈淇℃伅
+ *
+ * @param processInstanceIds 娴佺▼瀹炰緥id
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean deleteRunAndHisInstance(List<String> processInstanceIds) {
+ try {
+ // 1.鍒犻櫎杩愯涓祦绋嬪疄渚�
+ List<Task> list = QueryUtils.taskQuery(processInstanceIds).list();
+ List<Task> subTasks = StreamUtils.filter(list, e -> StringUtils.isNotBlank(e.getParentTaskId()));
+ if (CollUtil.isNotEmpty(subTasks)) {
+ subTasks.forEach(e -> taskService.deleteTask(e.getId()));
+ }
+ runtimeService.bulkDeleteProcessInstances(processInstanceIds, LoginHelper.getUserId() + "鍒犻櫎浜嗗綋鍓嶆祦绋嬬敵璇�");
+ // 2.鍒犻櫎鍘嗗彶璁板綍
+ List<HistoricProcessInstance> historicProcessInstanceList = QueryUtils.hisInstanceQuery(new HashSet<>(processInstanceIds)).list();
+ if (ObjectUtil.isNotEmpty(historicProcessInstanceList)) {
+ historyService.bulkDeleteHistoricProcessInstances(processInstanceIds);
+ }
+ wfTaskBackNodeService.deleteByInstanceIds(processInstanceIds);
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 鎸夌収涓氬姟id鍒犻櫎 杩愯涓殑瀹炰緥 鍒犻櫎绋嬪疄渚嬶紝鍒犻櫎鍘嗗彶璁板綍锛屽垹闄や笟鍔′笌娴佺▼鍏宠仈淇℃伅
+ *
+ * @param businessKeys 涓氬姟id
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean deleteRunAndHisInstanceByBusinessKeys(List<String> businessKeys) {
+ try {
+ // 1.鍒犻櫎杩愯涓祦绋嬪疄渚�
+ List<ActHiProcinst> actHiProcinsts = actHiProcinstService.selectByBusinessKeyIn(businessKeys);
+ if (CollUtil.isEmpty(actHiProcinsts)) {
+ log.warn("褰撳墠涓氬姟ID:{}鏌ヨ鍒版祦绋嬪疄渚嬩负绌猴紒", businessKeys);
+ return false;
+ }
+ List<String> processInstanceIds = StreamUtils.toList(actHiProcinsts, ActHiProcinst::getId);
+ List<Task> list = QueryUtils.taskQuery(processInstanceIds).list();
+ List<Task> subTasks = StreamUtils.filter(list, e -> StringUtils.isNotBlank(e.getParentTaskId()));
+ if (CollUtil.isNotEmpty(subTasks)) {
+ subTasks.forEach(e -> taskService.deleteTask(e.getId()));
+ }
+ runtimeService.bulkDeleteProcessInstances(processInstanceIds, LoginHelper.getUserId() + "鍒犻櫎浜嗗綋鍓嶆祦绋嬬敵璇�");
+ // 2.鍒犻櫎鍘嗗彶璁板綍
+ List<HistoricProcessInstance> historicProcessInstanceList = QueryUtils.hisInstanceQuery(new HashSet<>(processInstanceIds)).list();
+ if (ObjectUtil.isNotEmpty(historicProcessInstanceList)) {
+ historyService.bulkDeleteHistoricProcessInstances(processInstanceIds);
+ }
+ wfTaskBackNodeService.deleteByInstanceIds(processInstanceIds);
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 宸插畬鎴愮殑瀹炰緥 鍒犻櫎绋嬪疄渚嬶紝鍒犻櫎鍘嗗彶璁板綍锛屽垹闄や笟鍔′笌娴佺▼鍏宠仈淇℃伅
+ *
+ * @param processInstanceIds 娴佺▼瀹炰緥id
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean deleteFinishAndHisInstance(List<String> processInstanceIds) {
+ try {
+ historyService.bulkDeleteHistoricProcessInstances(processInstanceIds);
+ wfTaskBackNodeService.deleteByInstanceIds(processInstanceIds);
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 鎾ら攢娴佺▼鐢宠
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean cancelProcessApply(String processInstanceId) {
+ try {
+ ProcessInstance processInstance = QueryUtils.instanceQuery(processInstanceId)
+ .startedBy(String.valueOf(LoginHelper.getUserId())).singleResult();
+ if (ObjectUtil.isNull(processInstance)) {
+ throw new ServiceException("鎮ㄤ笉鏄祦绋嬪彂璧蜂汉,鎾ら攢澶辫触!");
+ }
+ if (processInstance.isSuspended()) {
+ throw new ServiceException(FlowConstant.MESSAGE_SUSPENDED);
+ }
+ BusinessStatusEnum.checkCancelStatus(processInstance.getBusinessStatus());
+ List<Task> taskList = QueryUtils.taskQuery(processInstanceId).list();
+ for (Task task : taskList) {
+ taskService.setAssignee(task.getId(), null);
+ taskService.addComment(task.getId(), processInstanceId, TaskStatusEnum.CANCEL.getStatus(), LoginHelper.getLoginUser().getNickname() + "锛氭挙閿�鐢宠");
+ }
+ HistoricTaskInstance historicTaskInstance = QueryUtils.hisTaskInstanceQuery().finished().orderByHistoricTaskInstanceEndTime().asc().list().get(0);
+ List<String> nodeIds = StreamUtils.toList(taskList, Task::getTaskDefinitionKey);
+ runtimeService.createChangeActivityStateBuilder()
+ .processInstanceId(processInstanceId)
+ .moveActivityIdsToSingleActivityId(nodeIds, historicTaskInstance.getTaskDefinitionKey()).changeState();
+ Task task = QueryUtils.taskQuery(processInstanceId).list().get(0);
+ taskService.setAssignee(task.getId(), historicTaskInstance.getAssignee());
+ //鑾峰彇骞惰缃戝叧鎵ц鍚庝繚鐣欑殑鎵ц瀹炰緥鏁版嵁
+ ExecutionChildByExecutionIdCmd childByExecutionIdCmd = new ExecutionChildByExecutionIdCmd(task.getExecutionId());
+ List<ExecutionEntity> executionEntities = managementService.executeCommand(childByExecutionIdCmd);
+ //鍒犻櫎娴佺▼瀹炰緥鍨冨溇鏁版嵁
+ for (ExecutionEntity executionEntity : executionEntities) {
+ DeleteExecutionCmd deleteExecutionCmd = new DeleteExecutionCmd(executionEntity.getId());
+ managementService.executeCommand(deleteExecutionCmd);
+ }
+ runtimeService.updateBusinessStatus(processInstanceId, BusinessStatusEnum.CANCEL.getStatus());
+ FlowProcessEventHandler processHandler = flowEventStrategy.getProcessHandler(processInstance.getProcessDefinitionKey());
+ if (processHandler != null) {
+ processHandler.handleProcess(processInstance.getBusinessKey(), BusinessStatusEnum.CANCEL.getStatus(), false);
+ }
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException("鎾ら攢澶辫触:" + e.getMessage());
+ }
+ }
+
+ /**
+ * 鍒嗛〉鏌ヨ褰撳墠鐧诲綍浜哄崟鎹�
+ *
+ * @param bo 鍙傛暟
+ */
+ @Override
+ public TableDataInfo<ProcessInstanceVo> getPageByCurrent(ProcessInstanceBo bo, PageQuery pageQuery) {
+ List<ProcessInstanceVo> list = new ArrayList<>();
+ HistoricProcessInstanceQuery query = QueryUtils.hisInstanceQuery();
+ query.startedBy(String.valueOf(LoginHelper.getUserId()));
+ if (StringUtils.isNotBlank(bo.getName())) {
+ query.processInstanceNameLikeIgnoreCase("%" + bo.getName() + "%");
+ }
+ if (StringUtils.isNotBlank(bo.getKey())) {
+ query.processDefinitionKey(bo.getKey());
+ }
+ if (StringUtils.isNotBlank(bo.getBusinessKey())) {
+ query.processInstanceBusinessKey(bo.getBusinessKey());
+ }
+ if (StringUtils.isNotBlank(bo.getCategoryCode())) {
+ query.processDefinitionCategory(bo.getCategoryCode());
+ }
+ query.orderByProcessInstanceStartTime().desc();
+ List<HistoricProcessInstance> historicProcessInstanceList = query.listPage(pageQuery.getFirstNum(), pageQuery.getPageSize());
+ List<TaskVo> taskVoList = new ArrayList<>();
+ if (CollUtil.isNotEmpty(historicProcessInstanceList)) {
+ List<String> processInstanceIds = StreamUtils.toList(historicProcessInstanceList, HistoricProcessInstance::getId);
+ List<Task> taskList = QueryUtils.taskQuery(processInstanceIds).list();
+ for (Task task : taskList) {
+ taskVoList.add(BeanUtil.toBean(task, TaskVo.class));
+ }
+ }
+ for (HistoricProcessInstance processInstance : historicProcessInstanceList) {
+ ProcessInstanceVo processInstanceVo = BeanUtil.toBean(processInstance, ProcessInstanceVo.class);
+ processInstanceVo.setBusinessStatusName(BusinessStatusEnum.findByStatus(processInstance.getBusinessStatus()));
+ if (CollUtil.isNotEmpty(taskVoList)) {
+ List<TaskVo> collect = StreamUtils.filter(taskVoList, e -> e.getProcessInstanceId().equals(processInstance.getId()));
+ processInstanceVo.setTaskVoList(CollUtil.isNotEmpty(collect) ? collect : Collections.emptyList());
+ }
+ list.add(processInstanceVo);
+ }
+ if (CollUtil.isNotEmpty(list)) {
+ List<String> processDefinitionIds = StreamUtils.toList(list, ProcessInstanceVo::getProcessDefinitionId);
+ List<WfNodeConfigVo> wfNodeConfigVoList = wfNodeConfigService.selectByDefIds(processDefinitionIds);
+ for (ProcessInstanceVo processInstanceVo : list) {
+ if (CollUtil.isNotEmpty(wfNodeConfigVoList)) {
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(processInstanceVo.getProcessDefinitionId()) && FlowConstant.TRUE.equals(e.getApplyUserTask())).findFirst().ifPresent(processInstanceVo::setWfNodeConfigVo);
+ }
+ }
+ }
+ long count = query.count();
+ TableDataInfo<ProcessInstanceVo> build = TableDataInfo.build();
+ build.setRows(list);
+ build.setTotal(count);
+ return build;
+ }
+
+ /**
+ * 浠诲姟鍌姙(缁欏綋鍓嶄换鍔″姙鐞嗕汉鍙戦�佺珯鍐呬俊锛岄偖浠讹紝鐭俊绛�)
+ *
+ * @param taskUrgingBo 浠诲姟鍌姙
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean taskUrging(TaskUrgingBo taskUrgingBo) {
+ try {
+ ProcessInstance processInstance = QueryUtils.instanceQuery(taskUrgingBo.getProcessInstanceId()).singleResult();
+ if (processInstance == null) {
+ throw new ServiceException("浠诲姟宸茬粨鏉燂紒");
+ }
+ String message = taskUrgingBo.getMessage();
+ if (StringUtils.isBlank(message)) {
+ message = "鎮ㄧ殑銆�" + processInstance.getName() + "銆戝崟鎹繕鏈鎵癸紝璇锋偍鍙婃椂澶勭悊銆�";
+ }
+ List<Task> list = QueryUtils.taskQuery(taskUrgingBo.getProcessInstanceId()).list();
+ WorkflowUtils.sendMessage(list, processInstance.getName(), taskUrgingBo.getMessageType(), message);
+ } catch (ServiceException e) {
+ throw new ServiceException(e.getMessage());
+ }
+ return true;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActTaskServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActTaskServiceImpl.java
new file mode 100644
index 0000000..1a4866d
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/ActTaskServiceImpl.java
@@ -0,0 +1,872 @@
+package org.dromara.workflow.service.impl;
+
+import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.util.ObjectUtil;
+import cn.hutool.core.util.StrUtil;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.domain.dto.RoleDTO;
+import org.dromara.common.core.domain.dto.UserDTO;
+import org.dromara.common.core.exception.ServiceException;
+import org.dromara.common.core.service.UserService;
+import org.dromara.common.core.utils.StreamUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.satoken.utils.LoginHelper;
+import org.dromara.common.tenant.helper.TenantHelper;
+import org.dromara.workflow.common.constant.FlowConstant;
+import org.dromara.workflow.common.enums.BusinessStatusEnum;
+import org.dromara.workflow.common.enums.TaskStatusEnum;
+import org.dromara.workflow.domain.ActHiTaskinst;
+import org.dromara.workflow.domain.WfTaskBackNode;
+import org.dromara.workflow.domain.bo.*;
+import org.dromara.workflow.domain.vo.*;
+import org.dromara.workflow.flowable.cmd.*;
+import org.dromara.workflow.flowable.strategy.FlowEventStrategy;
+import org.dromara.workflow.flowable.strategy.FlowProcessEventHandler;
+import org.dromara.workflow.flowable.strategy.FlowTaskEventHandler;
+import org.dromara.workflow.mapper.ActHiTaskinstMapper;
+import org.dromara.workflow.mapper.ActTaskMapper;
+import org.dromara.workflow.service.IActTaskService;
+import org.dromara.workflow.service.IWfDefinitionConfigService;
+import org.dromara.workflow.service.IWfNodeConfigService;
+import org.dromara.workflow.service.IWfTaskBackNodeService;
+import org.dromara.workflow.utils.ModelUtils;
+import org.dromara.workflow.utils.QueryUtils;
+import org.dromara.workflow.utils.WorkflowUtils;
+import org.flowable.common.engine.api.FlowableObjectNotFoundException;
+import org.flowable.common.engine.impl.identity.Authentication;
+import org.flowable.engine.*;
+import org.flowable.engine.history.HistoricProcessInstance;
+import org.flowable.engine.history.HistoricProcessInstanceQuery;
+import org.flowable.engine.impl.bpmn.behavior.ParallelMultiInstanceBehavior;
+import org.flowable.engine.impl.bpmn.behavior.SequentialMultiInstanceBehavior;
+import org.flowable.engine.impl.persistence.entity.ExecutionEntity;
+import org.flowable.engine.runtime.ProcessInstance;
+import org.flowable.identitylink.api.history.HistoricIdentityLink;
+import org.flowable.task.api.Task;
+import org.flowable.task.api.TaskQuery;
+import org.flowable.task.api.history.HistoricTaskInstance;
+import org.flowable.task.service.impl.persistence.entity.TaskEntity;
+import org.flowable.variable.api.persistence.entity.VariableInstance;
+import org.springframework.scheduling.annotation.Async;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.*;
+import java.util.stream.Collectors;
+
+import static org.dromara.workflow.common.constant.FlowConstant.*;
+
+/**
+ * 浠诲姟 鏈嶅姟灞傚疄鐜�
+ *
+ * @author may
+ */
+@RequiredArgsConstructor
+@Service
+public class ActTaskServiceImpl implements IActTaskService {
+
+ private final RuntimeService runtimeService;
+ private final TaskService taskService;
+ private final HistoryService historyService;
+ private final IdentityService identityService;
+ private final ManagementService managementService;
+ private final FlowEventStrategy flowEventStrategy;
+ private final ActTaskMapper actTaskMapper;
+ private final IWfTaskBackNodeService wfTaskBackNodeService;
+ private final ActHiTaskinstMapper actHiTaskinstMapper;
+ private final IWfNodeConfigService wfNodeConfigService;
+ private final IWfDefinitionConfigService wfDefinitionConfigService;
+ private final UserService userService;
+
+ /**
+ * 鍚姩浠诲姟
+ *
+ * @param startProcessBo 鍚姩娴佺▼鍙傛暟
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public Map<String, Object> startWorkFlow(StartProcessBo startProcessBo) {
+ Map<String, Object> map = new HashMap<>();
+ if (StringUtils.isBlank(startProcessBo.getBusinessKey())) {
+ throw new ServiceException("鍚姩宸ヤ綔娴佹椂蹇呴』鍖呭惈涓氬姟ID");
+ }
+ // 鍒ゆ柇褰撳墠涓氬姟鏄惁鍚姩杩囨祦绋�
+ HistoricProcessInstanceQuery query = QueryUtils.hisInstanceQuery();
+ HistoricProcessInstance historicProcessInstance = query.processInstanceBusinessKey(startProcessBo.getBusinessKey()).singleResult();
+ if (ObjectUtil.isNotEmpty(historicProcessInstance)) {
+ BusinessStatusEnum.checkStartStatus(historicProcessInstance.getBusinessStatus());
+ }
+ List<Task> taskResult = QueryUtils.taskQuery().processInstanceBusinessKey(startProcessBo.getBusinessKey()).list();
+ if (CollUtil.isNotEmpty(taskResult)) {
+ if (CollUtil.isNotEmpty(startProcessBo.getVariables())) {
+ taskService.setVariables(taskResult.get(0).getId(), startProcessBo.getVariables());
+ }
+ map.put(PROCESS_INSTANCE_ID, taskResult.get(0).getProcessInstanceId());
+ map.put("taskId", taskResult.get(0).getId());
+ return map;
+ }
+ WfDefinitionConfigVo wfDefinitionConfigVo = wfDefinitionConfigService.getByTableNameLastVersion(startProcessBo.getTableName());
+ if (wfDefinitionConfigVo == null) {
+ throw new ServiceException("璇峰埌娴佺▼瀹氫箟缁戝畾涓氬姟琛ㄥ悕涓庢祦绋婯EY锛�");
+ }
+ // 璁剧疆鍚姩浜�
+ identityService.setAuthenticatedUserId(String.valueOf(LoginHelper.getUserId()));
+ Authentication.setAuthenticatedUserId(String.valueOf(LoginHelper.getUserId()));
+ // 鍚姩娴佺▼瀹炰緥锛堟彁浜ょ敵璇凤級
+ Map<String, Object> variables = startProcessBo.getVariables();
+ // 鍚姩璺宠繃琛ㄨ揪寮�
+ variables.put(FLOWABLE_SKIP_EXPRESSION_ENABLED, true);
+ // 娴佺▼鍙戣捣浜�
+ variables.put(INITIATOR, (String.valueOf(LoginHelper.getUserId())));
+ ProcessInstance pi;
+ try {
+ if (TenantHelper.isEnable()) {
+ pi = runtimeService.startProcessInstanceByKeyAndTenantId(wfDefinitionConfigVo.getProcessKey(), startProcessBo.getBusinessKey(), variables, TenantHelper.getTenantId());
+ } else {
+ pi = runtimeService.startProcessInstanceByKey(wfDefinitionConfigVo.getProcessKey(), startProcessBo.getBusinessKey(), variables);
+ }
+ } catch (FlowableObjectNotFoundException e) {
+ throw new ServiceException("鎵句笉鍒板綋鍓嶃��" + wfDefinitionConfigVo.getProcessKey() + "銆戞祦绋嬪畾涔夛紒");
+ }
+ // 灏嗘祦绋嬪畾涔夊悕绉� 浣滀负 娴佺▼瀹炰緥鍚嶇О
+ runtimeService.setProcessInstanceName(pi.getProcessInstanceId(), pi.getProcessDefinitionName());
+ // 鐢宠浜烘墽琛屾祦绋�
+ List<Task> taskList = QueryUtils.taskQuery(pi.getId()).list();
+ if (taskList.size() > 1) {
+ throw new ServiceException("璇锋鏌ユ祦绋嬬涓�涓幆鑺傛槸鍚︿负鐢宠浜猴紒");
+ }
+
+ runtimeService.updateBusinessStatus(pi.getProcessInstanceId(), BusinessStatusEnum.DRAFT.getStatus());
+ taskService.setAssignee(taskList.get(0).getId(), LoginHelper.getUserId().toString());
+ taskService.setVariable(taskList.get(0).getId(), PROCESS_INSTANCE_ID, pi.getProcessInstanceId());
+ taskService.setVariable(taskList.get(0).getId(), BUSINESS_KEY, pi.getBusinessKey());
+ map.put("processInstanceId", pi.getProcessInstanceId());
+ map.put("taskId", taskList.get(0).getId());
+ return map;
+ }
+
+ /**
+ * 鍔炵悊浠诲姟
+ *
+ * @param completeTaskBo 鍔炵悊浠诲姟鍙傛暟
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean completeTask(CompleteTaskBo completeTaskBo) {
+ try {
+ List<RoleDTO> roles = LoginHelper.getLoginUser().getRoles();
+ String userId = String.valueOf(LoginHelper.getUserId());
+ TaskQuery taskQuery = QueryUtils.taskQuery();
+ taskQuery.taskId(completeTaskBo.getTaskId()).taskCandidateOrAssigned(userId);
+ if (CollUtil.isNotEmpty(roles)) {
+ List<String> groupIds = StreamUtils.toList(roles, e -> String.valueOf(e.getRoleId()));
+ taskQuery.taskCandidateGroupIn(groupIds);
+ }
+ Task task = taskQuery.singleResult();
+ if (task == null) {
+ throw new ServiceException(FlowConstant.MESSAGE_CURRENT_TASK_IS_NULL);
+ }
+ if (task.isSuspended()) {
+ throw new ServiceException(FlowConstant.MESSAGE_SUSPENDED);
+ }
+ ProcessInstance processInstance = QueryUtils.instanceQuery(task.getProcessInstanceId()).singleResult();
+ //鍔炵悊濮旀墭浠诲姟
+ if (ObjectUtil.isNotEmpty(task.getDelegationState()) && FlowConstant.PENDING.equals(task.getDelegationState().name())) {
+ taskService.resolveTask(completeTaskBo.getTaskId());
+ TaskEntity newTask = WorkflowUtils.createNewTask(task);
+ taskService.addComment(newTask.getId(), task.getProcessInstanceId(), TaskStatusEnum.PASS.getStatus(), StringUtils.isNotBlank(completeTaskBo.getMessage()) ? completeTaskBo.getMessage() : StrUtil.EMPTY);
+ taskService.complete(newTask.getId());
+ return true;
+ }
+ //闄勪欢涓婁紶
+ AttachmentCmd attachmentCmd = new AttachmentCmd(completeTaskBo.getFileId(), task.getId(), task.getProcessInstanceId());
+ managementService.executeCommand(attachmentCmd);
+ FlowProcessEventHandler processHandler = flowEventStrategy.getProcessHandler(processInstance.getProcessDefinitionKey());
+ String businessStatus = WorkflowUtils.getBusinessStatus(task.getProcessInstanceId());
+ if (BusinessStatusEnum.DRAFT.getStatus().equals(businessStatus) || BusinessStatusEnum.BACK.getStatus().equals(businessStatus) || BusinessStatusEnum.CANCEL.getStatus().equals(businessStatus)) {
+ if (processHandler != null) {
+ processHandler.handleProcess(processInstance.getBusinessKey(), businessStatus, true);
+ }
+ }
+ runtimeService.updateBusinessStatus(task.getProcessInstanceId(), BusinessStatusEnum.WAITING.getStatus());
+ String key = processInstance.getProcessDefinitionKey() + "_" + task.getTaskDefinitionKey();
+ FlowTaskEventHandler taskHandler = flowEventStrategy.getTaskHandler(key);
+ if (taskHandler != null) {
+ taskHandler.handleTask(task.getId(), processInstance.getBusinessKey());
+ }
+ //鍔炵悊鎰忚
+ taskService.addComment(completeTaskBo.getTaskId(), task.getProcessInstanceId(), TaskStatusEnum.PASS.getStatus(), StringUtils.isBlank(completeTaskBo.getMessage()) ? "鍚屾剰" : completeTaskBo.getMessage());
+ //鍔炵悊浠诲姟
+ taskService.setAssignee(task.getId(), userId);
+ if (CollUtil.isNotEmpty(completeTaskBo.getVariables())) {
+ taskService.complete(completeTaskBo.getTaskId(), completeTaskBo.getVariables());
+ } else {
+ taskService.complete(completeTaskBo.getTaskId());
+ }
+ //璁板綍鎵ц杩囩殑娴佺▼浠诲姟鑺傜偣
+ wfTaskBackNodeService.recordExecuteNode(task);
+ ProcessInstance pi = QueryUtils.instanceQuery(task.getProcessInstanceId()).singleResult();
+ if (pi == null) {
+ UpdateBusinessStatusCmd updateBusinessStatusCmd = new UpdateBusinessStatusCmd(task.getProcessInstanceId(), BusinessStatusEnum.FINISH.getStatus());
+ managementService.executeCommand(updateBusinessStatusCmd);
+ if (processHandler != null) {
+ processHandler.handleProcess(processInstance.getBusinessKey(), BusinessStatusEnum.FINISH.getStatus(), false);
+ }
+ } else {
+ List<Task> list = QueryUtils.taskQuery(task.getProcessInstanceId()).list();
+ for (Task t : list) {
+ if (ModelUtils.isUserTask(t.getProcessDefinitionId(), t.getTaskDefinitionKey())) {
+ List<HistoricIdentityLink> links = historyService.getHistoricIdentityLinksForTask(t.getId());
+ if (CollUtil.isEmpty(links) && StringUtils.isBlank(t.getAssignee())) {
+ throw new ServiceException("涓嬩竴鑺傜偣銆�" + t.getName() + "銆戞病鏈夊姙鐞嗕汉!");
+ }
+ }
+ }
+
+ if (CollUtil.isNotEmpty(list) && CollUtil.isNotEmpty(completeTaskBo.getWfCopyList())) {
+ TaskEntity newTask = WorkflowUtils.createNewTask(task);
+ taskService.addComment(newTask.getId(), task.getProcessInstanceId(), TaskStatusEnum.COPY.getStatus(), LoginHelper.getLoginUser().getNickname() + "銆愭妱閫併�戠粰" + String.join(",", StreamUtils.toList(completeTaskBo.getWfCopyList(), WfCopy::getUserName)));
+ taskService.complete(newTask.getId());
+ List<Task> taskList = QueryUtils.taskQuery(task.getProcessInstanceId()).list();
+ WorkflowUtils.createCopyTask(taskList, StreamUtils.toList(completeTaskBo.getWfCopyList(), WfCopy::getUserId));
+ }
+ sendMessage(list, processInstance.getName(), completeTaskBo.getMessageType(), null);
+ }
+ return true;
+ } catch (Exception e) {
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 鍙戦�佹秷鎭�
+ *
+ * @param list 浠诲姟
+ * @param name 娴佺▼鍚嶇О
+ * @param messageType 娑堟伅绫诲瀷
+ * @param message 娑堟伅鍐呭锛屼负绌哄垯鍙戦�侀粯璁ら厤缃殑娑堟伅鍐呭
+ */
+ @Async
+ public void sendMessage(List<Task> list, String name, List<String> messageType, String message) {
+ WorkflowUtils.sendMessage(list, name, messageType, message);
+ }
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勫緟鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @Override
+ public TableDataInfo<TaskVo> getPageByTaskWait(TaskBo taskBo, PageQuery pageQuery) {
+ QueryWrapper<TaskVo> queryWrapper = new QueryWrapper<>();
+ List<RoleDTO> roles = LoginHelper.getLoginUser().getRoles();
+ List<String> roleIds = StreamUtils.toList(roles, e -> String.valueOf(e.getRoleId()));
+ String userId = String.valueOf(LoginHelper.getUserId());
+ queryWrapper.eq("t.business_status_", BusinessStatusEnum.WAITING.getStatus());
+ queryWrapper.eq(TenantHelper.isEnable(), "t.tenant_id_", TenantHelper.getTenantId());
+ queryWrapper.and(w1 -> w1.eq("t.assignee_", userId).or(w2 -> w2.isNull("t.assignee_").apply("exists ( select LINK.ID_ from ACT_RU_IDENTITYLINK LINK where LINK.TASK_ID_ = t.ID_ and LINK.TYPE_ = 'candidate' " + "and (LINK.USER_ID_ = {0} or ( LINK.GROUP_ID_ IN " + getInParam(roleIds) + " ) ))", userId)));
+ if (StringUtils.isNotBlank(taskBo.getName())) {
+ queryWrapper.like("t.name_", taskBo.getName());
+ }
+ if (StringUtils.isNotBlank(taskBo.getProcessDefinitionName())) {
+ queryWrapper.like("t.processDefinitionName", taskBo.getProcessDefinitionName());
+ }
+ if (StringUtils.isNotBlank(taskBo.getProcessDefinitionKey())) {
+ queryWrapper.eq("t.processDefinitionKey", taskBo.getProcessDefinitionKey());
+ }
+ Page<TaskVo> page = actTaskMapper.getTaskWaitByPage(pageQuery.build(), queryWrapper);
+
+ List<TaskVo> taskList = page.getRecords();
+ if (CollUtil.isNotEmpty(taskList)) {
+ List<String> processDefinitionIds = StreamUtils.toList(taskList, TaskVo::getProcessDefinitionId);
+ List<WfNodeConfigVo> wfNodeConfigVoList = wfNodeConfigService.selectByDefIds(processDefinitionIds);
+ for (TaskVo task : taskList) {
+ task.setBusinessStatusName(BusinessStatusEnum.findByStatus(task.getBusinessStatus()));
+ task.setParticipantVo(WorkflowUtils.getCurrentTaskParticipant(task.getId()));
+ task.setMultiInstance(WorkflowUtils.isMultiInstance(task.getProcessDefinitionId(), task.getTaskDefinitionKey()) != null);
+ if (CollUtil.isNotEmpty(wfNodeConfigVoList)) {
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && FlowConstant.TRUE.equals(e.getApplyUserTask())).findFirst().ifPresent(task::setWfNodeConfigVo);
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && e.getNodeId().equals(task.getTaskDefinitionKey()) && FlowConstant.FALSE.equals(e.getApplyUserTask())).findFirst().ifPresent(task::setWfNodeConfigVo);
+ }
+ }
+ }
+ return TableDataInfo.build(page);
+ }
+
+ private String getInParam(List<String> param) {
+ StringBuilder sb = new StringBuilder();
+ sb.append("(");
+ for (int i = 0; i < param.size(); i++) {
+ sb.append("'").append(param.get(i)).append("'");
+ if (i != param.size() - 1) {
+ sb.append(",");
+ }
+ }
+ sb.append(")");
+ return sb.toString();
+ }
+
+ /**
+ * 鏌ヨ褰撳墠绉熸埛鎵�鏈夊緟鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @Override
+ public TableDataInfo<TaskVo> getPageByAllTaskWait(TaskBo taskBo, PageQuery pageQuery) {
+ TaskQuery query = QueryUtils.taskQuery();
+ if (StringUtils.isNotBlank(taskBo.getName())) {
+ query.taskNameLike("%" + taskBo.getName() + "%");
+ }
+ if (StringUtils.isNotBlank(taskBo.getProcessDefinitionName())) {
+ query.processDefinitionNameLike("%" + taskBo.getProcessDefinitionName() + "%");
+ }
+ if (StringUtils.isNotBlank(taskBo.getProcessDefinitionKey())) {
+ query.processDefinitionKey(taskBo.getProcessDefinitionKey());
+ }
+ query.orderByTaskCreateTime().desc();
+ List<Task> taskList = query.listPage(pageQuery.getFirstNum(), pageQuery.getPageSize());
+ List<ProcessInstance> processInstanceList = null;
+ if (CollUtil.isNotEmpty(taskList)) {
+ Set<String> processInstanceIds = StreamUtils.toSet(taskList, Task::getProcessInstanceId);
+ processInstanceList = QueryUtils.instanceQuery(processInstanceIds).list();
+ }
+ List<TaskVo> list = new ArrayList<>();
+ if (CollUtil.isNotEmpty(taskList)) {
+ List<String> processDefinitionIds = StreamUtils.toList(taskList, Task::getProcessDefinitionId);
+ List<WfNodeConfigVo> wfNodeConfigVoList = wfNodeConfigService.selectByDefIds(processDefinitionIds);
+ for (Task task : taskList) {
+ TaskVo taskVo = BeanUtil.toBean(task, TaskVo.class);
+ if (CollUtil.isNotEmpty(processInstanceList)) {
+ processInstanceList.stream().filter(e -> e.getId().equals(task.getProcessInstanceId())).findFirst().ifPresent(e -> {
+ taskVo.setBusinessStatus(e.getBusinessStatus());
+ taskVo.setBusinessStatusName(BusinessStatusEnum.findByStatus(taskVo.getBusinessStatus()));
+ taskVo.setProcessDefinitionKey(e.getProcessDefinitionKey());
+ taskVo.setProcessDefinitionName(e.getProcessDefinitionName());
+ taskVo.setProcessDefinitionVersion(e.getProcessDefinitionVersion());
+ taskVo.setBusinessKey(e.getBusinessKey());
+ });
+ }
+ taskVo.setAssignee(StringUtils.isNotBlank(task.getAssignee()) ? Long.valueOf(task.getAssignee()) : null);
+ taskVo.setParticipantVo(WorkflowUtils.getCurrentTaskParticipant(task.getId()));
+ taskVo.setMultiInstance(WorkflowUtils.isMultiInstance(task.getProcessDefinitionId(), task.getTaskDefinitionKey()) != null);
+ if (CollUtil.isNotEmpty(wfNodeConfigVoList)) {
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && FlowConstant.TRUE.equals(e.getApplyUserTask())).findFirst().ifPresent(taskVo::setWfNodeConfigVo);
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && e.getNodeId().equals(task.getTaskDefinitionKey()) && FlowConstant.FALSE.equals(e.getApplyUserTask())).findFirst().ifPresent(taskVo::setWfNodeConfigVo);
+ }
+ list.add(taskVo);
+ }
+ }
+ long count = query.count();
+ TableDataInfo<TaskVo> build = TableDataInfo.build();
+ build.setRows(list);
+ build.setTotal(count);
+ return build;
+ }
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勫凡鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @Override
+ public TableDataInfo<TaskVo> getPageByTaskFinish(TaskBo taskBo, PageQuery pageQuery) {
+ String userId = String.valueOf(LoginHelper.getUserId());
+ QueryWrapper<TaskVo> queryWrapper = new QueryWrapper<>();
+ queryWrapper.like(StringUtils.isNotBlank(taskBo.getName()), "t.name_", taskBo.getName());
+ queryWrapper.like(StringUtils.isNotBlank(taskBo.getProcessDefinitionName()), "t.processDefinitionName", taskBo.getProcessDefinitionName());
+ queryWrapper.eq(StringUtils.isNotBlank(taskBo.getProcessDefinitionKey()), "t.processDefinitionKey", taskBo.getProcessDefinitionKey());
+ queryWrapper.eq("t.assignee_", userId);
+ Page<TaskVo> page = actTaskMapper.getTaskFinishByPage(pageQuery.build(), queryWrapper);
+
+ List<TaskVo> taskList = page.getRecords();
+ if (CollUtil.isNotEmpty(taskList)) {
+ List<String> processDefinitionIds = StreamUtils.toList(taskList, TaskVo::getProcessDefinitionId);
+ List<WfNodeConfigVo> wfNodeConfigVoList = wfNodeConfigService.selectByDefIds(processDefinitionIds);
+ for (TaskVo task : taskList) {
+ task.setBusinessStatusName(BusinessStatusEnum.findByStatus(task.getBusinessStatus()));
+ if (CollUtil.isNotEmpty(wfNodeConfigVoList)) {
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && FlowConstant.TRUE.equals(e.getApplyUserTask())).findFirst().ifPresent(task::setWfNodeConfigVo);
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && e.getNodeId().equals(task.getTaskDefinitionKey()) && FlowConstant.FALSE.equals(e.getApplyUserTask())).findFirst().ifPresent(task::setWfNodeConfigVo);
+ }
+ }
+ }
+ return TableDataInfo.build(page);
+ }
+
+ /**
+ * 鏌ヨ褰撳墠鐢ㄦ埛鐨勬妱閫�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @Override
+ public TableDataInfo<TaskVo> getPageByTaskCopy(TaskBo taskBo, PageQuery pageQuery) {
+ QueryWrapper<TaskVo> queryWrapper = new QueryWrapper<>();
+ String userId = String.valueOf(LoginHelper.getUserId());
+ if (StringUtils.isNotBlank(taskBo.getName())) {
+ queryWrapper.like("t.name_", taskBo.getName());
+ }
+ if (StringUtils.isNotBlank(taskBo.getProcessDefinitionName())) {
+ queryWrapper.like("t.processDefinitionName", taskBo.getProcessDefinitionName());
+ }
+ if (StringUtils.isNotBlank(taskBo.getProcessDefinitionKey())) {
+ queryWrapper.eq("t.processDefinitionKey", taskBo.getProcessDefinitionKey());
+ }
+ queryWrapper.eq("t.assignee_", userId);
+ Page<TaskVo> page = actTaskMapper.getTaskCopyByPage(pageQuery.build(), queryWrapper);
+
+ List<TaskVo> taskList = page.getRecords();
+ if (CollUtil.isNotEmpty(taskList)) {
+ List<String> processDefinitionIds = StreamUtils.toList(taskList, TaskVo::getProcessDefinitionId);
+ List<WfNodeConfigVo> wfNodeConfigVoList = wfNodeConfigService.selectByDefIds(processDefinitionIds);
+ for (TaskVo task : taskList) {
+ task.setBusinessStatusName(BusinessStatusEnum.findByStatus(task.getBusinessStatus()));
+ if (CollUtil.isNotEmpty(wfNodeConfigVoList)) {
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && FlowConstant.TRUE.equals(e.getApplyUserTask())).findFirst().ifPresent(task::setWfNodeConfigVo);
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && e.getNodeId().equals(task.getTaskDefinitionKey()) && FlowConstant.FALSE.equals(e.getApplyUserTask())).findFirst().ifPresent(task::setWfNodeConfigVo);
+ }
+ }
+ }
+ return TableDataInfo.build(page);
+ }
+
+ /**
+ * 鏌ヨ褰撳墠绉熸埛鎵�鏈夊凡鍔炰换鍔�
+ *
+ * @param taskBo 鍙傛暟
+ */
+ @Override
+ public TableDataInfo<TaskVo> getPageByAllTaskFinish(TaskBo taskBo, PageQuery pageQuery) {
+ QueryWrapper<TaskVo> queryWrapper = new QueryWrapper<>();
+ queryWrapper.like(StringUtils.isNotBlank(taskBo.getName()), "t.name_", taskBo.getName());
+ queryWrapper.like(StringUtils.isNotBlank(taskBo.getProcessDefinitionName()), "t.processDefinitionName", taskBo.getProcessDefinitionName());
+ queryWrapper.eq(StringUtils.isNotBlank(taskBo.getProcessDefinitionKey()), "t.processDefinitionKey", taskBo.getProcessDefinitionKey());
+ Page<TaskVo> page = actTaskMapper.getTaskFinishByPage(pageQuery.build(), queryWrapper);
+
+ List<TaskVo> taskList = page.getRecords();
+ if (CollUtil.isNotEmpty(taskList)) {
+ List<String> processDefinitionIds = StreamUtils.toList(taskList, TaskVo::getProcessDefinitionId);
+ List<WfNodeConfigVo> wfNodeConfigVoList = wfNodeConfigService.selectByDefIds(processDefinitionIds);
+ for (TaskVo task : taskList) {
+ task.setBusinessStatusName(BusinessStatusEnum.findByStatus(task.getBusinessStatus()));
+ if (CollUtil.isNotEmpty(wfNodeConfigVoList)) {
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && FlowConstant.TRUE.equals(e.getApplyUserTask())).findFirst().ifPresent(task::setWfNodeConfigVo);
+ wfNodeConfigVoList.stream().filter(e -> e.getDefinitionId().equals(task.getProcessDefinitionId()) && e.getNodeId().equals(task.getTaskDefinitionKey()) && FlowConstant.FALSE.equals(e.getApplyUserTask())).findFirst().ifPresent(task::setWfNodeConfigVo);
+ }
+ }
+ }
+ return TableDataInfo.build(page);
+ }
+
+ /**
+ * 濮旀淳浠诲姟
+ *
+ * @param delegateBo 鍙傛暟
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean delegateTask(DelegateBo delegateBo) {
+ TaskQuery query = QueryUtils.taskQuery();
+ TaskEntity task = (TaskEntity) query.taskId(delegateBo.getTaskId()).taskCandidateOrAssigned(String.valueOf(LoginHelper.getUserId())).singleResult();
+ if (ObjectUtil.isEmpty(task)) {
+ throw new ServiceException(FlowConstant.MESSAGE_CURRENT_TASK_IS_NULL);
+ }
+ if (task.isSuspended()) {
+ throw new ServiceException(FlowConstant.MESSAGE_SUSPENDED);
+ }
+ try {
+ TaskEntity newTask = WorkflowUtils.createNewTask(task);
+ taskService.addComment(newTask.getId(), task.getProcessInstanceId(), TaskStatusEnum.PENDING.getStatus(), "銆�" + LoginHelper.getLoginUser().getNickname() + "銆戝娲剧粰銆�" + delegateBo.getNickName() + "銆�");
+ //濮旀墭浠诲姟
+ taskService.delegateTask(delegateBo.getTaskId(), delegateBo.getUserId());
+ //鍔炵悊鐢熸垚鐨勪换鍔¤褰�
+ taskService.complete(newTask.getId());
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 缁堟浠诲姟
+ *
+ * @param terminationBo 鍙傛暟
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean terminationTask(TerminationBo terminationBo) {
+ TaskQuery query = QueryUtils.taskQuery();
+ Task task = query.taskId(terminationBo.getTaskId()).singleResult();
+
+ if (ObjectUtil.isEmpty(task)) {
+ throw new ServiceException(FlowConstant.MESSAGE_CURRENT_TASK_IS_NULL);
+ }
+ if (task.isSuspended()) {
+ throw new ServiceException(FlowConstant.MESSAGE_SUSPENDED);
+ }
+ HistoricProcessInstance historicProcessInstance = QueryUtils.hisInstanceQuery().processInstanceId(task.getProcessInstanceId()).singleResult();
+ BusinessStatusEnum.checkInvalidStatus(historicProcessInstance.getBusinessStatus());
+ try {
+ if (StringUtils.isBlank(terminationBo.getComment())) {
+ terminationBo.setComment(LoginHelper.getLoginUser().getNickname() + "缁堟浜嗙敵璇�");
+ } else {
+ terminationBo.setComment(LoginHelper.getLoginUser().getNickname() + "缁堟浜嗙敵璇凤細" + terminationBo.getComment());
+ }
+ taskService.addComment(task.getId(), task.getProcessInstanceId(), TaskStatusEnum.TERMINATION.getStatus(), terminationBo.getComment());
+ List<Task> list = QueryUtils.taskQuery(task.getProcessInstanceId()).list();
+ if (CollUtil.isNotEmpty(list)) {
+ List<Task> subTasks = StreamUtils.filter(list, e -> StringUtils.isNotBlank(e.getParentTaskId()));
+ if (CollUtil.isNotEmpty(subTasks)) {
+ subTasks.forEach(e -> taskService.deleteTask(e.getId()));
+ }
+ runtimeService.updateBusinessStatus(task.getProcessInstanceId(), BusinessStatusEnum.TERMINATION.getStatus());
+ runtimeService.deleteProcessInstance(task.getProcessInstanceId(), StrUtil.EMPTY);
+ }
+ FlowProcessEventHandler processHandler = flowEventStrategy.getProcessHandler(historicProcessInstance.getProcessDefinitionKey());
+ if (processHandler != null) {
+ processHandler.handleProcess(historicProcessInstance.getBusinessKey(), BusinessStatusEnum.TERMINATION.getStatus(), false);
+ }
+ return true;
+ } catch (Exception e) {
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 杞姙浠诲姟
+ *
+ * @param transmitBo 鍙傛暟
+ */
+ @Override
+ public boolean transferTask(TransmitBo transmitBo) {
+ Task task = QueryUtils.taskQuery().taskId(transmitBo.getTaskId()).taskCandidateOrAssigned(String.valueOf(LoginHelper.getUserId())).singleResult();
+ if (ObjectUtil.isEmpty(task)) {
+ throw new ServiceException(FlowConstant.MESSAGE_CURRENT_TASK_IS_NULL);
+ }
+ if (task.isSuspended()) {
+ throw new ServiceException(FlowConstant.MESSAGE_SUSPENDED);
+ }
+ try {
+ TaskEntity newTask = WorkflowUtils.createNewTask(task);
+ taskService.addComment(newTask.getId(), task.getProcessInstanceId(), TaskStatusEnum.TRANSFER.getStatus(), StringUtils.isNotBlank(transmitBo.getComment()) ? transmitBo.getComment() : LoginHelper.getUsername() + "杞姙浜嗕换鍔�");
+ taskService.complete(newTask.getId());
+ taskService.setAssignee(task.getId(), transmitBo.getUserId());
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 浼氱浠诲姟鍔犵
+ *
+ * @param addMultiBo 鍙傛暟
+ */
+ @Override
+ public boolean addMultiInstanceExecution(AddMultiBo addMultiBo) {
+ TaskQuery taskQuery = QueryUtils.taskQuery();
+ taskQuery.taskId(addMultiBo.getTaskId());
+ if (!LoginHelper.isSuperAdmin() && !LoginHelper.isTenantAdmin()) {
+ taskQuery.taskCandidateOrAssigned(String.valueOf(LoginHelper.getUserId()));
+ }
+ Task task = taskQuery.singleResult();
+ if (ObjectUtil.isEmpty(task)) {
+ throw new ServiceException(FlowConstant.MESSAGE_CURRENT_TASK_IS_NULL);
+ }
+ if (task.isSuspended()) {
+ throw new ServiceException(FlowConstant.MESSAGE_SUSPENDED);
+ }
+ String taskDefinitionKey = task.getTaskDefinitionKey();
+ String processInstanceId = task.getProcessInstanceId();
+ String processDefinitionId = task.getProcessDefinitionId();
+
+ try {
+ MultiInstanceVo multiInstanceVo = WorkflowUtils.isMultiInstance(processDefinitionId, taskDefinitionKey);
+ if (multiInstanceVo == null) {
+ throw new ServiceException("褰撳墠鐜妭涓嶆槸浼氱鑺傜偣");
+ }
+ if (multiInstanceVo.getType() instanceof ParallelMultiInstanceBehavior) {
+ for (Long assignee : addMultiBo.getAssignees()) {
+ runtimeService.addMultiInstanceExecution(taskDefinitionKey, processInstanceId, Collections.singletonMap(multiInstanceVo.getAssignee(), assignee));
+ }
+ } else if (multiInstanceVo.getType() instanceof SequentialMultiInstanceBehavior) {
+ AddSequenceMultiInstanceCmd addSequenceMultiInstanceCmd = new AddSequenceMultiInstanceCmd(task.getExecutionId(), multiInstanceVo.getAssigneeList(), addMultiBo.getAssignees());
+ managementService.executeCommand(addSequenceMultiInstanceCmd);
+ }
+ List<String> assigneeNames = addMultiBo.getAssigneeNames();
+ String username = LoginHelper.getUsername();
+ TaskEntity newTask = WorkflowUtils.createNewTask(task);
+ taskService.addComment(newTask.getId(), processInstanceId, TaskStatusEnum.SIGN.getStatus(), username + "鍔犵銆�" + String.join(StringUtils.SEPARATOR, assigneeNames) + "銆�");
+ taskService.complete(newTask.getId());
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 浼氱浠诲姟鍑忕
+ *
+ * @param deleteMultiBo 鍙傛暟
+ */
+ @Override
+ public boolean deleteMultiInstanceExecution(DeleteMultiBo deleteMultiBo) {
+ TaskQuery taskQuery = QueryUtils.taskQuery();
+ taskQuery.taskId(deleteMultiBo.getTaskId());
+ if (!LoginHelper.isSuperAdmin() && !LoginHelper.isTenantAdmin()) {
+ taskQuery.taskCandidateOrAssigned(String.valueOf(LoginHelper.getUserId()));
+ }
+ Task task = taskQuery.singleResult();
+ if (ObjectUtil.isEmpty(task)) {
+ throw new ServiceException(FlowConstant.MESSAGE_CURRENT_TASK_IS_NULL);
+ }
+ if (task.isSuspended()) {
+ throw new ServiceException(FlowConstant.MESSAGE_SUSPENDED);
+ }
+ String taskDefinitionKey = task.getTaskDefinitionKey();
+ String processInstanceId = task.getProcessInstanceId();
+ String processDefinitionId = task.getProcessDefinitionId();
+ try {
+ MultiInstanceVo multiInstanceVo = WorkflowUtils.isMultiInstance(processDefinitionId, taskDefinitionKey);
+ if (multiInstanceVo == null) {
+ throw new ServiceException("褰撳墠鐜妭涓嶆槸浼氱鑺傜偣");
+ }
+ if (multiInstanceVo.getType() instanceof ParallelMultiInstanceBehavior) {
+ for (String executionId : deleteMultiBo.getExecutionIds()) {
+ runtimeService.deleteMultiInstanceExecution(executionId, false);
+ }
+ for (String taskId : deleteMultiBo.getTaskIds()) {
+ historyService.deleteHistoricTaskInstance(taskId);
+ }
+ } else if (multiInstanceVo.getType() instanceof SequentialMultiInstanceBehavior) {
+ DeleteSequenceMultiInstanceCmd deleteSequenceMultiInstanceCmd = new DeleteSequenceMultiInstanceCmd(task.getAssignee(), task.getExecutionId(), multiInstanceVo.getAssigneeList(), deleteMultiBo.getAssigneeIds());
+ managementService.executeCommand(deleteSequenceMultiInstanceCmd);
+ }
+ List<String> assigneeNames = deleteMultiBo.getAssigneeNames();
+ String username = LoginHelper.getUsername();
+ TaskEntity newTask = WorkflowUtils.createNewTask(task);
+ taskService.addComment(newTask.getId(), processInstanceId, TaskStatusEnum.SIGN_OFF.getStatus(), username + "鍑忕銆�" + String.join(StringUtils.SEPARATOR, assigneeNames) + "銆�");
+ taskService.complete(newTask.getId());
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException(e.getMessage());
+ }
+ }
+
+ /**
+ * 椹冲洖瀹℃壒
+ *
+ * @param backProcessBo 鍙傛暟
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public String backProcess(BackProcessBo backProcessBo) {
+ TaskQuery query = QueryUtils.taskQuery();
+ String userId = String.valueOf(LoginHelper.getUserId());
+ Task task = query.taskId(backProcessBo.getTaskId()).taskCandidateOrAssigned(userId).singleResult();
+ if (ObjectUtil.isEmpty(task)) {
+ throw new ServiceException(FlowConstant.MESSAGE_CURRENT_TASK_IS_NULL);
+ }
+ if (task.isSuspended()) {
+ throw new ServiceException(FlowConstant.MESSAGE_SUSPENDED);
+ }
+ try {
+ String processInstanceId = task.getProcessInstanceId();
+ ProcessInstance processInstance = QueryUtils.instanceQuery(task.getProcessInstanceId()).singleResult();
+ //鑾峰彇骞惰缃戝叧鎵ц鍚庝繚鐣欑殑鎵ц瀹炰緥鏁版嵁
+ ExecutionChildByExecutionIdCmd childByExecutionIdCmd = new ExecutionChildByExecutionIdCmd(task.getExecutionId());
+ List<ExecutionEntity> executionEntities = managementService.executeCommand(childByExecutionIdCmd);
+ //鏍¢獙鍗曟嵁
+ BusinessStatusEnum.checkBackStatus(processInstance.getBusinessStatus());
+ //鍒ゆ柇鏄惁鏈夊涓换鍔�
+ List<Task> taskList = QueryUtils.taskQuery(processInstanceId).list();
+ String backTaskDefinitionKey = backProcessBo.getTargetActivityId();
+ taskService.addComment(task.getId(), processInstanceId, TaskStatusEnum.BACK.getStatus(), StringUtils.isNotBlank(backProcessBo.getMessage()) ? backProcessBo.getMessage() : "閫�鍥�");
+ if (taskList.size() > 1) {
+ //褰撳墠澶氫釜浠诲姟椹冲洖鍒板崟涓妭鐐�
+ runtimeService.createChangeActivityStateBuilder().processInstanceId(processInstanceId).moveActivityIdsToSingleActivityId(taskList.stream().map(Task::getTaskDefinitionKey).distinct().collect(Collectors.toList()), backTaskDefinitionKey).changeState();
+ ActHiTaskinst actHiTaskinst = new ActHiTaskinst();
+ actHiTaskinst.setAssignee(userId);
+ actHiTaskinst.setId(task.getId());
+ actHiTaskinstMapper.updateById(actHiTaskinst);
+ } else {
+ //褰撳墠鍗曚釜鑺傜偣椹冲洖鍗曚釜鑺傜偣
+ runtimeService.createChangeActivityStateBuilder().processInstanceId(processInstanceId).moveActivityIdTo(task.getTaskDefinitionKey(), backTaskDefinitionKey).changeState();
+ }
+ //鍒犻櫎骞惰鐜妭鏈姙鐞嗚褰�
+ MultiInstanceVo multiInstance = WorkflowUtils.isMultiInstance(task.getProcessDefinitionId(), task.getTaskDefinitionKey());
+ if (multiInstance == null && taskList.size() > 1) {
+ List<Task> tasks = StreamUtils.filter(taskList, e -> !e.getTaskDefinitionKey().equals(task.getTaskDefinitionKey()));
+ actHiTaskinstMapper.deleteBatchIds(StreamUtils.toList(tasks, Task::getId));
+ }
+
+
+ List<HistoricTaskInstance> instanceList = QueryUtils.hisTaskInstanceQuery(processInstanceId).finished().orderByHistoricTaskInstanceEndTime().desc().list();
+ List<Task> list = QueryUtils.taskQuery(processInstanceId).list();
+ for (Task t : list) {
+ instanceList.stream().filter(e -> e.getTaskDefinitionKey().equals(t.getTaskDefinitionKey())).findFirst().ifPresent(e -> {
+ taskService.setAssignee(t.getId(), e.getAssignee());
+ });
+ }
+ //鍙戦�佹秷鎭�
+ String message = "鎮ㄧ殑銆�" + processInstance.getName() + "銆戝崟鎹凡缁忚椹冲洖锛岃鎮ㄦ敞鎰忔煡鏀躲��";
+ sendMessage(list, processInstance.getName(), backProcessBo.getMessageType(), message);
+ //鍒犻櫎娴佺▼瀹炰緥鍨冨溇鏁版嵁
+ for (ExecutionEntity executionEntity : executionEntities) {
+ DeleteExecutionCmd deleteExecutionCmd = new DeleteExecutionCmd(executionEntity.getId());
+ managementService.executeCommand(deleteExecutionCmd);
+ }
+
+ WfTaskBackNode wfTaskBackNode = wfTaskBackNodeService.getListByInstanceIdAndNodeId(task.getProcessInstanceId(), backProcessBo.getTargetActivityId());
+ if (ObjectUtil.isNotNull(wfTaskBackNode) && wfTaskBackNode.getOrderNo() == 0) {
+ runtimeService.updateBusinessStatus(processInstanceId, BusinessStatusEnum.BACK.getStatus());
+ FlowProcessEventHandler processHandler = flowEventStrategy.getProcessHandler(processInstance.getProcessDefinitionKey());
+ if (processHandler != null) {
+ processHandler.handleProcess(processInstance.getBusinessKey(), BusinessStatusEnum.BACK.getStatus(), false);
+ }
+ }
+ //鍒犻櫎椹冲洖鍚庣殑娴佺▼鑺傜偣
+ wfTaskBackNodeService.deleteBackTaskNode(processInstanceId, backProcessBo.getTargetActivityId());
+ } catch (Exception e) {
+ throw new ServiceException(e.getMessage());
+ }
+ return task.getProcessInstanceId();
+ }
+
+ /**
+ * 淇敼浠诲姟鍔炵悊浜�
+ *
+ * @param taskIds 浠诲姟id
+ * @param userId 鍔炵悊浜篿d
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean updateAssignee(String[] taskIds, String userId) {
+ try {
+ List<Task> list = QueryUtils.taskQuery().taskIds(Arrays.asList(taskIds)).list();
+ for (Task task : list) {
+ taskService.setAssignee(task.getId(), userId);
+ }
+ } catch (Exception e) {
+ throw new ServiceException("淇敼澶辫触锛�" + e.getMessage());
+ }
+ return true;
+ }
+
+ /**
+ * 鏌ヨ娴佺▼鍙橀噺
+ *
+ * @param taskId 浠诲姟id
+ */
+ @Override
+ public List<VariableVo> getInstanceVariable(String taskId) {
+ List<VariableVo> variableVoList = new ArrayList<>();
+ Map<String, VariableInstance> variableInstances = taskService.getVariableInstances(taskId);
+ if (CollUtil.isNotEmpty(variableInstances)) {
+ for (Map.Entry<String, VariableInstance> entry : variableInstances.entrySet()) {
+ VariableVo variableVo = new VariableVo();
+ variableVo.setKey(entry.getKey());
+ variableVo.setValue(entry.getValue().getValue().toString());
+ variableVoList.add(variableVo);
+ }
+ }
+ return variableVoList;
+ }
+
+ /**
+ * 鏌ヨ宸ヤ綔娴佷换鍔$敤鎴烽�夋嫨鍔犵浜哄憳
+ *
+ * @param taskId 浠诲姟id
+ * @return
+ */
+ @Override
+ @SuppressWarnings("unchecked")
+ public String getTaskUserIdsByAddMultiInstance(String taskId) {
+ Task task = QueryUtils.taskQuery().taskId(taskId).singleResult();
+ if (task == null) {
+ throw new ServiceException("浠诲姟涓嶅瓨鍦�");
+ }
+ MultiInstanceVo multiInstance = WorkflowUtils.isMultiInstance(task.getProcessDefinitionId(), task.getTaskDefinitionKey());
+ if (multiInstance == null) {
+ return "";
+ }
+ List<Long> userIds;
+ if (multiInstance.getType() instanceof SequentialMultiInstanceBehavior) {
+ userIds = (List<Long>) runtimeService.getVariable(task.getExecutionId(), multiInstance.getAssigneeList());
+ } else {
+ List<Task> list = QueryUtils.taskQuery(task.getProcessInstanceId()).list();
+ userIds = StreamUtils.toList(list, e -> Long.valueOf(e.getAssignee()));
+ }
+ return StringUtils.join(userIds, StringUtils.SEPARATOR);
+ }
+
+ /**
+ * 鏌ヨ宸ヤ綔娴侀�夋嫨鍑忕浜哄憳
+ *
+ * @param taskId 浠诲姟id 浠诲姟id
+ */
+ @Override
+ @SuppressWarnings("unchecked")
+ public List<TaskVo> getListByDeleteMultiInstance(String taskId) {
+ Task task = QueryUtils.taskQuery().taskId(taskId).singleResult();
+ List<Task> taskList = QueryUtils.taskQuery(task.getProcessInstanceId()).list();
+ MultiInstanceVo multiInstance = WorkflowUtils.isMultiInstance(task.getProcessDefinitionId(), task.getTaskDefinitionKey());
+ List<TaskVo> taskListVo = new ArrayList<>();
+ if (multiInstance == null) {
+ return List.of();
+ }
+ List<Long> assigneeList = new ArrayList<>();
+ if (multiInstance.getType() instanceof SequentialMultiInstanceBehavior) {
+ List<Object> variable = (List<Object>) runtimeService.getVariable(task.getExecutionId(), multiInstance.getAssigneeList());
+ for (Object o : variable) {
+ assigneeList.add(Long.valueOf(o.toString()));
+ }
+ }
+
+ if (multiInstance.getType() instanceof SequentialMultiInstanceBehavior) {
+ List<Long> userIds = StreamUtils.filter(assigneeList, e -> !String.valueOf(e).equals(task.getAssignee()));
+ List<UserDTO> userList = userService.selectListByIds(userIds);
+ for (Long userId : userIds) {
+ TaskVo taskVo = new TaskVo();
+ taskVo.setId("涓茶浼氱");
+ taskVo.setExecutionId("涓茶浼氱");
+ taskVo.setProcessInstanceId(task.getProcessInstanceId());
+ taskVo.setName(task.getName());
+ taskVo.setAssignee(userId);
+ if (CollUtil.isNotEmpty(userList)) {
+ userList.stream().filter(u -> u.getUserId().toString().equals(userId.toString())).findFirst().ifPresent(u -> taskVo.setAssigneeName(u.getNickName()));
+ }
+ taskListVo.add(taskVo);
+ }
+ return taskListVo;
+ } else if (multiInstance.getType() instanceof ParallelMultiInstanceBehavior) {
+ List<Task> tasks = StreamUtils.filter(taskList, e -> StringUtils.isBlank(e.getParentTaskId()) && !e.getExecutionId().equals(task.getExecutionId()) && e.getTaskDefinitionKey().equals(task.getTaskDefinitionKey()));
+ if (CollUtil.isNotEmpty(tasks)) {
+ List<Long> userIds = StreamUtils.toList(tasks, e -> Long.valueOf(e.getAssignee()));
+ List<UserDTO> userList = userService.selectListByIds(userIds);
+ for (Task t : tasks) {
+ TaskVo taskVo = new TaskVo();
+ taskVo.setId(t.getId());
+ taskVo.setExecutionId(t.getExecutionId());
+ taskVo.setProcessInstanceId(t.getProcessInstanceId());
+ taskVo.setName(t.getName());
+ taskVo.setAssignee(Long.valueOf(t.getAssignee()));
+ if (CollUtil.isNotEmpty(userList)) {
+ userList.stream().filter(u -> u.getUserId().toString().equals(t.getAssignee())).findFirst().ifPresent(e -> taskVo.setAssigneeName(e.getNickName()));
+ }
+ taskListVo.add(taskVo);
+ }
+ return taskListVo;
+ }
+ }
+ return List.of();
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/TestLeaveServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/TestLeaveServiceImpl.java
new file mode 100644
index 0000000..bee5627
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/TestLeaveServiceImpl.java
@@ -0,0 +1,121 @@
+package org.dromara.workflow.service.impl;
+
+import cn.hutool.core.collection.CollUtil;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.utils.MapstructUtils;
+import org.dromara.common.core.utils.StreamUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.mybatis.core.domain.BaseEntity;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.workflow.domain.TestLeave;
+import org.dromara.workflow.domain.bo.TestLeaveBo;
+import org.dromara.workflow.domain.vo.TestLeaveVo;
+import org.dromara.workflow.mapper.TestLeaveMapper;
+import org.dromara.workflow.service.IActProcessInstanceService;
+import org.dromara.workflow.service.ITestLeaveService;
+import org.dromara.workflow.utils.WorkflowUtils;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.Collection;
+import java.util.List;
+
+/**
+ * 璇峰亣Service涓氬姟灞傚鐞�
+ *
+ * @author may
+ * @date 2023-07-21
+ */
+@RequiredArgsConstructor
+@Service
+public class TestLeaveServiceImpl implements ITestLeaveService {
+
+ private final TestLeaveMapper baseMapper;
+ private final IActProcessInstanceService actProcessInstanceService;
+
+ /**
+ * 鏌ヨ璇峰亣
+ */
+ @Override
+ public TestLeaveVo queryById(Long id) {
+ TestLeaveVo testLeaveVo = baseMapper.selectVoById(id);
+ WorkflowUtils.setProcessInstanceVo(testLeaveVo, String.valueOf(id));
+ return testLeaveVo;
+ }
+
+ /**
+ * 鏌ヨ璇峰亣鍒楄〃
+ */
+ @Override
+ public TableDataInfo<TestLeaveVo> queryPageList(TestLeaveBo bo, PageQuery pageQuery) {
+ LambdaQueryWrapper<TestLeave> lqw = buildQueryWrapper(bo);
+ Page<TestLeaveVo> result = baseMapper.selectVoPage(pageQuery.build(), lqw);
+ TableDataInfo<TestLeaveVo> build = TableDataInfo.build(result);
+ List<TestLeaveVo> rows = build.getRows();
+ if (CollUtil.isNotEmpty(rows)) {
+ List<String> ids = StreamUtils.toList(rows, e -> String.valueOf(e.getId()));
+ WorkflowUtils.setProcessInstanceListVo(rows, ids, "id");
+ }
+ return build;
+ }
+
+ /**
+ * 鏌ヨ璇峰亣鍒楄〃
+ */
+ @Override
+ public List<TestLeaveVo> queryList(TestLeaveBo bo) {
+ LambdaQueryWrapper<TestLeave> lqw = buildQueryWrapper(bo);
+ return baseMapper.selectVoList(lqw);
+ }
+
+ private LambdaQueryWrapper<TestLeave> buildQueryWrapper(TestLeaveBo bo) {
+ LambdaQueryWrapper<TestLeave> lqw = Wrappers.lambdaQuery();
+ lqw.eq(StringUtils.isNotBlank(bo.getLeaveType()), TestLeave::getLeaveType, bo.getLeaveType());
+ lqw.ge(bo.getStartLeaveDays() != null, TestLeave::getLeaveDays, bo.getStartLeaveDays());
+ lqw.le(bo.getEndLeaveDays() != null, TestLeave::getLeaveDays, bo.getEndLeaveDays());
+ lqw.orderByDesc(BaseEntity::getCreateTime);
+ return lqw;
+ }
+
+ /**
+ * 鏂板璇峰亣
+ */
+ @Override
+ public TestLeaveVo insertByBo(TestLeaveBo bo) {
+ TestLeave add = MapstructUtils.convert(bo, TestLeave.class);
+ boolean flag = baseMapper.insert(add) > 0;
+ if (flag) {
+ bo.setId(add.getId());
+ }
+ TestLeaveVo testLeaveVo = MapstructUtils.convert(add, TestLeaveVo.class);
+ WorkflowUtils.setProcessInstanceVo(testLeaveVo, String.valueOf(add.getId()));
+ return testLeaveVo;
+ }
+
+ /**
+ * 淇敼璇峰亣
+ */
+ @Override
+ public TestLeaveVo updateByBo(TestLeaveBo bo) {
+ TestLeave update = MapstructUtils.convert(bo, TestLeave.class);
+ baseMapper.updateById(update);
+ TestLeaveVo testLeaveVo = MapstructUtils.convert(update, TestLeaveVo.class);
+ WorkflowUtils.setProcessInstanceVo(testLeaveVo, String.valueOf(update.getId()));
+ return testLeaveVo;
+ }
+
+ /**
+ * 鎵归噺鍒犻櫎璇峰亣
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public Boolean deleteWithValidByIds(Collection<Long> ids) {
+ List<String> idList = StreamUtils.toList(ids, String::valueOf);
+ actProcessInstanceService.deleteRunAndHisInstanceByBusinessKeys(idList);
+ return baseMapper.deleteBatchIds(ids) > 0;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfCategoryServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfCategoryServiceImpl.java
new file mode 100644
index 0000000..c5cb288
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfCategoryServiceImpl.java
@@ -0,0 +1,129 @@
+package org.dromara.workflow.service.impl;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.utils.MapstructUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.workflow.domain.WfCategory;
+import org.dromara.workflow.domain.bo.WfCategoryBo;
+import org.dromara.workflow.domain.vo.WfCategoryVo;
+import org.dromara.workflow.mapper.WfCategoryMapper;
+import org.dromara.workflow.service.IWfCategoryService;
+import org.dromara.workflow.utils.QueryUtils;
+import org.flowable.engine.RepositoryService;
+import org.flowable.engine.repository.Deployment;
+import org.flowable.engine.repository.Model;
+import org.flowable.engine.repository.ProcessDefinition;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.Collection;
+import java.util.List;
+
+/**
+ * 娴佺▼鍒嗙被Service涓氬姟灞傚鐞�
+ *
+ * @author may
+ * @date 2023-06-28
+ */
+@RequiredArgsConstructor
+@Service
+public class WfCategoryServiceImpl implements IWfCategoryService {
+
+ private final WfCategoryMapper baseMapper;
+
+ private final RepositoryService repositoryService;
+
+ /**
+ * 鏌ヨ娴佺▼鍒嗙被
+ */
+ @Override
+ public WfCategoryVo queryById(Long id) {
+ return baseMapper.selectVoById(id);
+ }
+
+
+ /**
+ * 鏌ヨ娴佺▼鍒嗙被鍒楄〃
+ */
+ @Override
+ public List<WfCategoryVo> queryList(WfCategoryBo bo) {
+ LambdaQueryWrapper<WfCategory> lqw = buildQueryWrapper(bo);
+ return baseMapper.selectVoList(lqw);
+ }
+
+ private LambdaQueryWrapper<WfCategory> buildQueryWrapper(WfCategoryBo bo) {
+ LambdaQueryWrapper<WfCategory> lqw = Wrappers.lambdaQuery();
+ lqw.like(StringUtils.isNotBlank(bo.getCategoryName()), WfCategory::getCategoryName, bo.getCategoryName());
+ lqw.eq(StringUtils.isNotBlank(bo.getCategoryCode()), WfCategory::getCategoryCode, bo.getCategoryCode());
+ return lqw;
+ }
+
+ /**
+ * 鏂板娴佺▼鍒嗙被
+ */
+ @Override
+ public Boolean insertByBo(WfCategoryBo bo) {
+ WfCategory add = MapstructUtils.convert(bo, WfCategory.class);
+ validEntityBeforeSave(add);
+ boolean flag = baseMapper.insert(add) > 0;
+ if (flag) {
+ bo.setId(add.getId());
+ }
+ return flag;
+ }
+
+ /**
+ * 淇敼娴佺▼鍒嗙被
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public Boolean updateByBo(WfCategoryBo bo) {
+ WfCategory update = MapstructUtils.convert(bo, WfCategory.class);
+ validEntityBeforeSave(update);
+ WfCategoryVo wfCategoryVo = baseMapper.selectVoById(bo.getId());
+ List<ProcessDefinition> processDefinitionList = QueryUtils.definitionQuery().processDefinitionCategory(wfCategoryVo.getCategoryCode()).list();
+ for (ProcessDefinition processDefinition : processDefinitionList) {
+ repositoryService.setProcessDefinitionCategory(processDefinition.getId(), bo.getCategoryCode());
+ }
+ List<Deployment> deploymentList = QueryUtils.deploymentQuery().deploymentCategory(wfCategoryVo.getCategoryCode()).list();
+ for (Deployment deployment : deploymentList) {
+ repositoryService.setDeploymentCategory(deployment.getId(), bo.getCategoryCode());
+ }
+ List<Model> modelList = QueryUtils.modelQuery().modelCategory(wfCategoryVo.getCategoryCode()).list();
+ for (Model model : modelList) {
+ model.setCategory(bo.getCategoryCode());
+ repositoryService.saveModel(model);
+ }
+ return baseMapper.updateById(update) > 0;
+ }
+
+ /**
+ * 淇濆瓨鍓嶇殑鏁版嵁鏍¢獙
+ */
+ private void validEntityBeforeSave(WfCategory entity) {
+ //TODO 鍋氫竴浜涙暟鎹牎楠�,濡傚敮涓�绾︽潫
+ }
+
+ /**
+ * 鎵归噺鍒犻櫎娴佺▼鍒嗙被
+ */
+ @Override
+ public Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid) {
+ if (isValid) {
+ //TODO 鍋氫竴浜涗笟鍔′笂鐨勬牎楠�,鍒ゆ柇鏄惁闇�瑕佹牎楠�
+ }
+ return baseMapper.deleteBatchIds(ids) > 0;
+ }
+
+ /**
+ * 鎸夌収绫诲埆缂栫爜鏌ヨ
+ *
+ * @param categoryCode 鍒嗙被姣斿悧
+ */
+ @Override
+ public WfCategory queryByCategoryCode(String categoryCode) {
+ return baseMapper.selectOne(new LambdaQueryWrapper<WfCategory>().eq(WfCategory::getCategoryCode, categoryCode));
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfDefinitionConfigServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfDefinitionConfigServiceImpl.java
new file mode 100644
index 0000000..9478825
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfDefinitionConfigServiceImpl.java
@@ -0,0 +1,117 @@
+package org.dromara.workflow.service.impl;
+
+import cn.hutool.core.collection.CollUtil;
+import org.dromara.common.core.utils.MapstructUtils;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import lombok.RequiredArgsConstructor;
+import org.dromara.workflow.domain.WfDefinitionConfig;
+import org.dromara.workflow.domain.bo.WfDefinitionConfigBo;
+import org.dromara.workflow.domain.vo.WfDefinitionConfigVo;
+import org.dromara.workflow.service.IWfDefinitionConfigService;
+import org.springframework.stereotype.Service;
+import org.dromara.workflow.mapper.WfDefinitionConfigMapper;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.List;
+import java.util.Collection;
+
+/**
+ * 娴佺▼瀹氫箟閰嶇疆Service涓氬姟灞傚鐞�
+ *
+ * @author may
+ * @date 2024-03-18
+ */
+@RequiredArgsConstructor
+@Service
+public class WfDefinitionConfigServiceImpl implements IWfDefinitionConfigService {
+
+ private final WfDefinitionConfigMapper baseMapper;
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆
+ */
+ @Override
+ public WfDefinitionConfigVo getByDefId(String definitionId) {
+ return baseMapper.selectVoOne(new LambdaQueryWrapper<WfDefinitionConfig>().eq(WfDefinitionConfig::getDefinitionId, definitionId));
+ }
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆
+ *
+ * @param tableName 琛ㄥ悕
+ * @return 缁撴灉
+ */
+ @Override
+ public WfDefinitionConfigVo getByTableNameLastVersion(String tableName) {
+ List<WfDefinitionConfigVo> wfDefinitionConfigVos = baseMapper.selectVoList(
+ new LambdaQueryWrapper<WfDefinitionConfig>().eq(WfDefinitionConfig::getTableName, tableName).orderByDesc(WfDefinitionConfig::getVersion));
+ if (CollUtil.isNotEmpty(wfDefinitionConfigVos)) {
+ return wfDefinitionConfigVos.get(0);
+ }
+ return null;
+ }
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆
+ *
+ * @param definitionId 娴佺▼瀹氫箟id
+ * @param tableName 琛ㄥ悕
+ * @return 缁撴灉
+ */
+ @Override
+ public WfDefinitionConfigVo getByDefIdAndTableName(String definitionId, String tableName) {
+ return baseMapper.selectVoOne(new LambdaQueryWrapper<WfDefinitionConfig>()
+ .eq(WfDefinitionConfig::getDefinitionId, definitionId)
+ .eq(WfDefinitionConfig::getTableName, tableName));
+ }
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆鎺掗櫎褰撳墠鏌ヨ鐨勬祦绋嬪畾涔�
+ *
+ * @param tableName 琛ㄥ悕
+ * @param definitionId 娴佺▼瀹氫箟id
+ */
+ @Override
+ public List<WfDefinitionConfigVo> getByTableNameNotDefId(String tableName, String definitionId) {
+ return baseMapper.selectVoList(new LambdaQueryWrapper<WfDefinitionConfig>()
+ .eq(WfDefinitionConfig::getTableName, tableName)
+ .ne(WfDefinitionConfig::getDefinitionId, definitionId));
+ }
+
+ /**
+ * 鏌ヨ娴佺▼瀹氫箟閰嶇疆鍒楄〃
+ */
+ @Override
+ public List<WfDefinitionConfigVo> queryList(List<String> definitionIds) {
+ return baseMapper.selectVoList(new LambdaQueryWrapper<WfDefinitionConfig>().in(WfDefinitionConfig::getDefinitionId, definitionIds));
+ }
+
+ /**
+ * 鏂板娴佺▼瀹氫箟閰嶇疆
+ */
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public Boolean saveOrUpdate(WfDefinitionConfigBo bo) {
+ WfDefinitionConfig add = MapstructUtils.convert(bo, WfDefinitionConfig.class);
+ baseMapper.delete(new LambdaQueryWrapper<WfDefinitionConfig>().eq(WfDefinitionConfig::getTableName, bo.getTableName()));
+ add.setTableName(add.getTableName().toLowerCase());
+ boolean flag = baseMapper.insertOrUpdate(add);
+ if (baseMapper.insertOrUpdate(add)) {
+ bo.setId(add.getId());
+ }
+ return flag;
+ }
+
+ /**
+ * 鎵归噺鍒犻櫎娴佺▼瀹氫箟閰嶇疆
+ */
+ @Override
+ public Boolean deleteByIds(Collection<Long> ids) {
+ return baseMapper.deleteBatchIds(ids) > 0;
+ }
+
+ @Override
+ public Boolean deleteByDefIds(Collection<String> ids) {
+ return baseMapper.delete(new LambdaQueryWrapper<WfDefinitionConfig>().in(WfDefinitionConfig::getDefinitionId, ids)) > 0;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfFormManageServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfFormManageServiceImpl.java
new file mode 100644
index 0000000..e0850d7
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfFormManageServiceImpl.java
@@ -0,0 +1,111 @@
+package org.dromara.workflow.service.impl;
+
+import org.dromara.common.core.utils.MapstructUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.mybatis.core.page.TableDataInfo;
+import org.dromara.common.mybatis.core.page.PageQuery;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import lombok.RequiredArgsConstructor;
+import org.dromara.workflow.common.enums.FormTypeEnum;
+import org.springframework.stereotype.Service;
+import org.dromara.workflow.domain.bo.WfFormManageBo;
+import org.dromara.workflow.domain.vo.WfFormManageVo;
+import org.dromara.workflow.domain.WfFormManage;
+import org.dromara.workflow.mapper.WfFormManageMapper;
+import org.dromara.workflow.service.IWfFormManageService;
+
+import java.util.List;
+import java.util.Collection;
+
+/**
+ * 琛ㄥ崟绠$悊Service涓氬姟灞傚鐞�
+ *
+ * @author may
+ * @date 2024-03-29
+ */
+@RequiredArgsConstructor
+@Service
+public class WfFormManageServiceImpl implements IWfFormManageService {
+
+ private final WfFormManageMapper baseMapper;
+
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊
+ */
+ @Override
+ public WfFormManageVo queryById(Long id) {
+ return baseMapper.selectVoById(id);
+ }
+
+ @Override
+ public List<WfFormManageVo> queryByIds(List<Long> ids) {
+ return baseMapper.selectVoBatchIds(ids);
+ }
+
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊鍒楄〃
+ */
+ @Override
+ public TableDataInfo<WfFormManageVo> queryPageList(WfFormManageBo bo, PageQuery pageQuery) {
+ LambdaQueryWrapper<WfFormManage> lqw = buildQueryWrapper(bo);
+ Page<WfFormManageVo> result = baseMapper.selectVoPage(pageQuery.build(), lqw);
+ return TableDataInfo.build(result);
+ }
+
+ @Override
+ public List<WfFormManageVo> selectList() {
+ List<WfFormManageVo> wfFormManageVos = baseMapper.selectVoList(new LambdaQueryWrapper<WfFormManage>().orderByDesc(WfFormManage::getUpdateTime));
+ for (WfFormManageVo wfFormManageVo : wfFormManageVos) {
+ wfFormManageVo.setFormTypeName(FormTypeEnum.findByType(wfFormManageVo.getFormType()));
+ }
+ return wfFormManageVos;
+ }
+
+ /**
+ * 鏌ヨ琛ㄥ崟绠$悊鍒楄〃
+ */
+ @Override
+ public List<WfFormManageVo> queryList(WfFormManageBo bo) {
+ LambdaQueryWrapper<WfFormManage> lqw = buildQueryWrapper(bo);
+ return baseMapper.selectVoList(lqw);
+ }
+
+ private LambdaQueryWrapper<WfFormManage> buildQueryWrapper(WfFormManageBo bo) {
+ LambdaQueryWrapper<WfFormManage> lqw = Wrappers.lambdaQuery();
+ lqw.like(StringUtils.isNotBlank(bo.getFormName()), WfFormManage::getFormName, bo.getFormName());
+ lqw.eq(StringUtils.isNotBlank(bo.getFormType()), WfFormManage::getFormType, bo.getFormType());
+ return lqw;
+ }
+
+ /**
+ * 鏂板琛ㄥ崟绠$悊
+ */
+ @Override
+ public Boolean insertByBo(WfFormManageBo bo) {
+ WfFormManage add = MapstructUtils.convert(bo, WfFormManage.class);
+ boolean flag = baseMapper.insert(add) > 0;
+ if (flag) {
+ bo.setId(add.getId());
+ }
+ return flag;
+ }
+
+ /**
+ * 淇敼琛ㄥ崟绠$悊
+ */
+ @Override
+ public Boolean updateByBo(WfFormManageBo bo) {
+ WfFormManage update = MapstructUtils.convert(bo, WfFormManage.class);
+ return baseMapper.updateById(update) > 0;
+ }
+
+ /**
+ * 鎵归噺鍒犻櫎琛ㄥ崟绠$悊
+ */
+ @Override
+ public Boolean deleteByIds(Collection<Long> ids) {
+ return baseMapper.deleteBatchIds(ids) > 0;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfNodeConfigServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfNodeConfigServiceImpl.java
new file mode 100644
index 0000000..c677102
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfNodeConfigServiceImpl.java
@@ -0,0 +1,75 @@
+package org.dromara.workflow.service.impl;
+
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.util.ObjectUtil;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.utils.StreamUtils;
+import org.dromara.workflow.domain.vo.WfFormManageVo;
+import org.dromara.workflow.service.IWfFormManageService;
+import org.springframework.stereotype.Service;
+import org.dromara.workflow.domain.vo.WfNodeConfigVo;
+import org.dromara.workflow.domain.WfNodeConfig;
+import org.dromara.workflow.mapper.WfNodeConfigMapper;
+import org.dromara.workflow.service.IWfNodeConfigService;
+
+import java.util.Collection;
+import java.util.List;
+
+/**
+ * 鑺傜偣閰嶇疆Service涓氬姟灞傚鐞�
+ *
+ * @author may
+ * @date 2024-03-30
+ */
+@RequiredArgsConstructor
+@Service
+public class WfNodeConfigServiceImpl implements IWfNodeConfigService {
+
+ private final WfNodeConfigMapper baseMapper;
+ private final IWfFormManageService wfFormManageService;
+
+ /**
+ * 鏌ヨ鑺傜偣閰嶇疆
+ */
+ @Override
+ public WfNodeConfigVo queryById(Long id) {
+ return baseMapper.selectVoById(id);
+ }
+
+ /**
+ * 淇濆瓨鑺傜偣閰嶇疆
+ */
+ @Override
+ public Boolean saveOrUpdate(List<WfNodeConfig> list) {
+ return baseMapper.insertOrUpdateBatch(list);
+ }
+
+ /**
+ * 鎵归噺鍒犻櫎鑺傜偣閰嶇疆
+ */
+ @Override
+ public Boolean deleteByIds(Collection<Long> ids) {
+ return baseMapper.deleteBatchIds(ids) > 0;
+ }
+
+
+
+ @Override
+ public Boolean deleteByDefIds(Collection<String> ids) {
+ return baseMapper.delete(new LambdaQueryWrapper<WfNodeConfig>().in(WfNodeConfig::getDefinitionId, ids)) > 0;
+ }
+
+ @Override
+ public List<WfNodeConfigVo> selectByDefIds(Collection<String> ids) {
+ List<WfNodeConfigVo> wfNodeConfigVos = baseMapper.selectVoList(new LambdaQueryWrapper<WfNodeConfig>().in(WfNodeConfig::getDefinitionId, ids));
+ if (CollUtil.isNotEmpty(wfNodeConfigVos)) {
+ List<Long> formIds = StreamUtils.toList(wfNodeConfigVos, WfNodeConfigVo::getFormId);
+ List<WfFormManageVo> wfFormManageVos = wfFormManageService.queryByIds(formIds);
+ for (WfNodeConfigVo wfNodeConfigVo : wfNodeConfigVos) {
+ wfFormManageVos.stream().filter(e -> ObjectUtil.equals(e.getId(), wfNodeConfigVo.getFormId())).findFirst().ifPresent(wfNodeConfigVo::setWfFormManageVo);
+ }
+ }
+ return wfNodeConfigVos;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfTaskBackNodeServiceImpl.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfTaskBackNodeServiceImpl.java
new file mode 100644
index 0000000..0992f6f
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/service/impl/WfTaskBackNodeServiceImpl.java
@@ -0,0 +1,141 @@
+package org.dromara.workflow.service.impl;
+
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.util.ObjectUtil;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import lombok.RequiredArgsConstructor;
+import org.dromara.common.core.exception.ServiceException;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.satoken.utils.LoginHelper;
+import org.dromara.workflow.domain.WfTaskBackNode;
+import org.dromara.workflow.domain.vo.MultiInstanceVo;
+import org.dromara.workflow.mapper.WfTaskBackNodeMapper;
+import org.dromara.workflow.service.IWfTaskBackNodeService;
+import org.dromara.workflow.utils.WorkflowUtils;
+import org.flowable.task.api.Task;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import static org.dromara.workflow.common.constant.FlowConstant.MULTI_INSTANCE;
+import static org.dromara.workflow.common.constant.FlowConstant.USER_TASK;
+
+
+/**
+ * 鑺傜偣椹冲洖璁板綍Service涓氬姟灞傚鐞�
+ *
+ * @author may
+ * @date 2024-03-13
+ */
+@RequiredArgsConstructor
+@Service
+public class WfTaskBackNodeServiceImpl implements IWfTaskBackNodeService {
+
+ private final WfTaskBackNodeMapper wfTaskBackNodeMapper;
+
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public void recordExecuteNode(Task task) {
+ List<WfTaskBackNode> list = getListByInstanceId(task.getProcessInstanceId());
+ WfTaskBackNode wfTaskBackNode = new WfTaskBackNode();
+ wfTaskBackNode.setNodeId(task.getTaskDefinitionKey());
+ wfTaskBackNode.setNodeName(task.getName());
+ wfTaskBackNode.setInstanceId(task.getProcessInstanceId());
+ wfTaskBackNode.setAssignee(String.valueOf(LoginHelper.getUserId()));
+ MultiInstanceVo multiInstance = WorkflowUtils.isMultiInstance(task.getProcessDefinitionId(), task.getTaskDefinitionKey());
+ if (ObjectUtil.isNotEmpty(multiInstance)) {
+ wfTaskBackNode.setTaskType(MULTI_INSTANCE);
+ } else {
+ wfTaskBackNode.setTaskType(USER_TASK);
+ }
+ if (CollUtil.isEmpty(list)) {
+ wfTaskBackNode.setOrderNo(0);
+ wfTaskBackNodeMapper.insert(wfTaskBackNode);
+ } else {
+ WfTaskBackNode taskNode = list.stream().filter(e -> e.getNodeId().equals(wfTaskBackNode.getNodeId()) && e.getOrderNo() == 0).findFirst().orElse(null);
+ if (ObjectUtil.isEmpty(taskNode)) {
+ wfTaskBackNode.setOrderNo(list.get(0).getOrderNo() + 1);
+ WfTaskBackNode node = getListByInstanceIdAndNodeId(wfTaskBackNode.getInstanceId(), wfTaskBackNode.getNodeId());
+ if (ObjectUtil.isNotEmpty(node)) {
+ node.setAssignee(node.getAssignee() + StringUtils.SEPARATOR + LoginHelper.getUserId());
+ wfTaskBackNodeMapper.updateById(node);
+ } else {
+ wfTaskBackNodeMapper.insert(wfTaskBackNode);
+ }
+ }
+ }
+ }
+
+ @Override
+ public List<WfTaskBackNode> getListByInstanceId(String processInstanceId) {
+ LambdaQueryWrapper<WfTaskBackNode> wrapper = new LambdaQueryWrapper<>();
+ wrapper.eq(WfTaskBackNode::getInstanceId, processInstanceId);
+ wrapper.orderByDesc(WfTaskBackNode::getOrderNo);
+ return wfTaskBackNodeMapper.selectList(wrapper);
+ }
+
+ @Override
+ public WfTaskBackNode getListByInstanceIdAndNodeId(String processInstanceId, String nodeId) {
+ LambdaQueryWrapper<WfTaskBackNode> queryWrapper = new LambdaQueryWrapper<>();
+ queryWrapper.eq(WfTaskBackNode::getInstanceId, processInstanceId);
+ queryWrapper.eq(WfTaskBackNode::getNodeId, nodeId);
+ return wfTaskBackNodeMapper.selectOne(queryWrapper);
+ }
+
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean deleteBackTaskNode(String processInstanceId, String targetActivityId) {
+ try {
+ LambdaQueryWrapper<WfTaskBackNode> queryWrapper = new LambdaQueryWrapper<>();
+ queryWrapper.eq(WfTaskBackNode::getInstanceId, processInstanceId);
+ queryWrapper.eq(WfTaskBackNode::getNodeId, targetActivityId);
+ WfTaskBackNode actTaskNode = wfTaskBackNodeMapper.selectOne(queryWrapper);
+ if (ObjectUtil.isNotNull(actTaskNode)) {
+ Integer orderNo = actTaskNode.getOrderNo();
+ List<WfTaskBackNode> taskNodeList = getListByInstanceId(processInstanceId);
+ List<Long> ids = new ArrayList<>();
+ if (CollUtil.isNotEmpty(taskNodeList)) {
+ for (WfTaskBackNode taskNode : taskNodeList) {
+ if (taskNode.getOrderNo() >= orderNo) {
+ ids.add(taskNode.getId());
+ }
+ }
+ }
+ if (CollUtil.isNotEmpty(ids)) {
+ wfTaskBackNodeMapper.deleteBatchIds(ids);
+ }
+ }
+ return true;
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ServiceException("鍒犻櫎澶辫触");
+ }
+ }
+
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public boolean deleteByInstanceId(String processInstanceId) {
+ LambdaQueryWrapper<WfTaskBackNode> wrapper = new LambdaQueryWrapper<>();
+ wrapper.eq(WfTaskBackNode::getInstanceId, processInstanceId);
+ List<WfTaskBackNode> list = wfTaskBackNodeMapper.selectList(wrapper);
+ int delete = wfTaskBackNodeMapper.delete(wrapper);
+ if (list.size() != delete) {
+ throw new ServiceException("鍒犻櫎澶辫触");
+ }
+ return true;
+ }
+
+ @Override
+ public boolean deleteByInstanceIds(List<String> processInstanceIds) {
+ LambdaQueryWrapper<WfTaskBackNode> wrapper = new LambdaQueryWrapper<>();
+ wrapper.in(WfTaskBackNode::getInstanceId, processInstanceIds);
+ List<WfTaskBackNode> list = wfTaskBackNodeMapper.selectList(wrapper);
+ int delete = wfTaskBackNodeMapper.delete(wrapper);
+ if (list.size() != delete) {
+ throw new ServiceException("鍒犻櫎澶辫触");
+ }
+ return true;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/ModelUtils.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/ModelUtils.java
new file mode 100644
index 0000000..7c5377e
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/ModelUtils.java
@@ -0,0 +1,289 @@
+package org.dromara.workflow.utils;
+
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.collection.CollectionUtil;
+import cn.hutool.core.io.IoUtil;
+import cn.hutool.core.util.ObjectUtil;
+import cn.hutool.core.util.StrUtil;
+import com.fasterxml.jackson.databind.JsonNode;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import lombok.AccessLevel;
+import lombok.NoArgsConstructor;
+import org.dromara.common.core.utils.SpringUtils;
+import org.dromara.common.core.utils.StreamUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.json.utils.JsonUtils;
+import org.dromara.workflow.domain.vo.MultiInstanceVo;
+import org.flowable.bpmn.converter.BpmnXMLConverter;
+import org.flowable.bpmn.model.*;
+import org.flowable.bpmn.model.Process;
+import org.flowable.editor.language.json.converter.BpmnJsonConverter;
+import org.flowable.engine.ProcessEngine;
+
+import javax.xml.stream.XMLInputFactory;
+import javax.xml.stream.XMLStreamException;
+import javax.xml.stream.XMLStreamReader;
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.rmi.ServerException;
+import java.util.*;
+import java.util.stream.Collectors;
+
+/**
+ * 妯″瀷宸ュ叿
+ *
+ * @author may
+ */
+@NoArgsConstructor(access = AccessLevel.PRIVATE)
+public class ModelUtils {
+
+ private static final ProcessEngine PROCESS_ENGINE = SpringUtils.getBean(ProcessEngine.class);
+
+ public static BpmnModel xmlToBpmnModel(String xml) throws IOException {
+ if (xml == null) {
+ throw new ServerException("xml涓嶈兘涓虹┖");
+ }
+ try {
+ InputStream inputStream = new ByteArrayInputStream(StrUtil.utf8Bytes(xml));
+ XMLInputFactory factory = XMLInputFactory.newInstance();
+ XMLStreamReader reader = factory.createXMLStreamReader(inputStream);
+ return new BpmnXMLConverter().convertToBpmnModel(reader);
+ } catch (XMLStreamException e) {
+ throw new ServerException(e.getMessage());
+ }
+ }
+
+ /**
+ * bpmnModel杞负xml
+ *
+ * @param jsonBytes json
+ */
+ public static byte[] bpmnJsonToXmlBytes(byte[] jsonBytes) throws IOException {
+ if (jsonBytes == null) {
+ return new byte[0];
+ }
+ // 1. json瀛楄妭鐮佽浆鎴� BpmnModel 瀵硅薄
+ ObjectMapper objectMapper = JsonUtils.getObjectMapper();
+ JsonNode jsonNode = objectMapper.readTree(jsonBytes);
+ BpmnModel bpmnModel = new BpmnJsonConverter().convertToBpmnModel(jsonNode);
+
+ if (bpmnModel.getProcesses().isEmpty()) {
+ return new byte[0];
+ }
+ // 2.灏哹pmnModel杞负xml
+ return new BpmnXMLConverter().convertToXML(bpmnModel);
+ }
+
+ /**
+ * xml杞负bpmnModel
+ *
+ * @param xmlBytes xml
+ */
+ public static BpmnModel xmlToBpmnModel(byte[] xmlBytes) throws XMLStreamException {
+ ByteArrayInputStream byteArrayInputStream = IoUtil.toStream(xmlBytes);
+ XMLInputFactory xif = XMLInputFactory.newInstance();
+ XMLStreamReader xtr = xif.createXMLStreamReader(byteArrayInputStream);
+ return new BpmnXMLConverter().convertToBpmnModel(xtr);
+ }
+
+ /**
+ * 鏍¢獙妯″瀷
+ *
+ * @param bpmnModel bpmn妯″瀷
+ */
+ public static void checkBpmnModel(BpmnModel bpmnModel) throws ServerException {
+ Collection<FlowElement> flowElements = bpmnModel.getMainProcess().getFlowElements();
+
+ checkBpmnNode(flowElements, false);
+
+ List<SubProcess> subProcessList = flowElements.stream().filter(SubProcess.class::isInstance).map(SubProcess.class::cast).collect(Collectors.toList());
+ if (!CollUtil.isEmpty(subProcessList)) {
+ for (SubProcess subProcess : subProcessList) {
+ Collection<FlowElement> subProcessFlowElements = subProcess.getFlowElements();
+ checkBpmnNode(subProcessFlowElements, true);
+ }
+ }
+ List<MultiInstanceVo> multiInstanceVoList = new ArrayList<>();
+ for (FlowElement flowElement : flowElements) {
+ if (flowElement instanceof UserTask && ObjectUtil.isNotEmpty(((UserTask) flowElement).getLoopCharacteristics()) && StringUtils.isNotBlank(((UserTask) flowElement).getLoopCharacteristics().getInputDataItem())) {
+ MultiInstanceVo multiInstanceVo = new MultiInstanceVo();
+ multiInstanceVo.setAssigneeList(((UserTask) flowElement).getLoopCharacteristics().getInputDataItem());
+ multiInstanceVoList.add(multiInstanceVo);
+ }
+ }
+
+ if (CollectionUtil.isNotEmpty(multiInstanceVoList) && multiInstanceVoList.size() > 1) {
+ Map<String, List<MultiInstanceVo>> assigneeListGroup = StreamUtils.groupByKey(multiInstanceVoList, MultiInstanceVo::getAssigneeList);
+ for (Map.Entry<String, List<MultiInstanceVo>> entry : assigneeListGroup.entrySet()) {
+ List<MultiInstanceVo> value = entry.getValue();
+ if (CollectionUtil.isNotEmpty(value) && value.size() > 1) {
+ String key = entry.getKey();
+ throw new ServerException("浼氱浜哄憳闆嗗悎銆�" + key + "銆戦噸澶�,璇烽噸鏂拌缃泦鍚圞EY");
+ }
+ }
+ }
+ }
+
+ /**
+ * 鏍¢獙bpmn鑺傜偣鏄惁鍚堟硶
+ *
+ * @param flowElements 鑺傜偣闆嗗悎
+ * @param subtask 鏄惁瀛愭祦绋�
+ */
+ private static void checkBpmnNode(Collection<FlowElement> flowElements, boolean subtask) throws ServerException {
+
+ if (CollUtil.isEmpty(flowElements)) {
+ throw new ServerException(subtask ? "瀛愭祦绋嬪繀椤诲瓨鍦ㄨ妭鐐�" : "蹇呴』瀛樺湪鑺傜偣锛�");
+ }
+
+ List<StartEvent> startEventList = flowElements.stream().filter(StartEvent.class::isInstance).map(StartEvent.class::cast).collect(Collectors.toList());
+ if (CollUtil.isEmpty(startEventList)) {
+ throw new ServerException(subtask ? "瀛愭祦绋嬪繀椤诲瓨鍦ㄥ紑濮嬭妭鐐�" : "蹇呴』瀛樺湪寮�濮嬭妭鐐癸紒");
+ }
+
+ if (startEventList.size() > 1) {
+ throw new ServerException(subtask ? "瀛愭祦绋嬪彧鑳藉瓨鍦ㄤ竴涓紑濮嬭妭鐐�" : "鍙兘瀛樺湪涓�涓紑濮嬭妭鐐癸紒");
+ }
+
+ StartEvent startEvent = startEventList.get(0);
+ List<SequenceFlow> outgoingFlows = startEvent.getOutgoingFlows();
+ if (CollUtil.isEmpty(outgoingFlows)) {
+ throw new ServerException(subtask ? "瀛愭祦绋嬫祦绋嬭妭鐐逛负绌猴紝璇疯嚦灏戣璁′竴鏉′富绾挎祦绋嬶紒" : "娴佺▼鑺傜偣涓虹┖锛岃鑷冲皯璁捐涓�鏉′富绾挎祦绋嬶紒");
+ }
+
+ FlowElement targetFlowElement = outgoingFlows.get(0).getTargetFlowElement();
+ if (!(targetFlowElement instanceof UserTask) && !subtask) {
+ throw new ServerException("寮�濮嬭妭鐐瑰悗绗竴涓妭鐐瑰繀椤绘槸鐢ㄦ埛浠诲姟锛�");
+ }
+ //寮�濮嬭妭鐐瑰悗绗竴涓妭鐐圭敵璇蜂汉鑺傜偣
+ if ((targetFlowElement instanceof UserTask) && !subtask) {
+ UserTask userTask = (UserTask) targetFlowElement;
+ if (StringUtils.isBlank(userTask.getFormKey())) {
+ throw new ServerException("鐢宠浜鸿妭鐐瑰繀椤婚�夋嫨琛ㄥ崟锛�");
+ }
+ }
+ List<EndEvent> endEventList = flowElements.stream().filter(EndEvent.class::isInstance).map(EndEvent.class::cast).collect(Collectors.toList());
+ if (CollUtil.isEmpty(endEventList)) {
+ throw new ServerException(subtask ? "瀛愭祦绋嬪繀椤诲瓨鍦ㄧ粨鏉熻妭鐐癸紒" : "蹇呴』瀛樺湪缁撴潫鑺傜偣锛�");
+ }
+ }
+
+ /**
+ * 鑾峰彇娴佺▼鍏ㄩ儴鐢ㄦ埛鑺傜偣
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ public static List<UserTask> getUserTaskFlowElements(String processDefinitionId) {
+ BpmnModel bpmnModel = PROCESS_ENGINE.getRepositoryService().getBpmnModel(processDefinitionId);
+ List<UserTask> list = new ArrayList<>();
+ List<Process> processes = bpmnModel.getProcesses();
+ Collection<FlowElement> flowElements = processes.get(0).getFlowElements();
+ buildUserTaskFlowElements(flowElements, list);
+ return list;
+ }
+
+ /**
+ * 閫掑綊鑾峰彇鎵�鏈夎妭鐐�
+ *
+ * @param flowElements 鑺傜偣淇℃伅
+ * @param list 闆嗗悎
+ */
+ private static void buildUserTaskFlowElements(Collection<FlowElement> flowElements, List<UserTask> list) {
+ for (FlowElement flowElement : flowElements) {
+ if (flowElement instanceof SubProcess) {
+ Collection<FlowElement> subFlowElements = ((SubProcess) flowElement).getFlowElements();
+ buildUserTaskFlowElements(subFlowElements, list);
+ } else if (flowElement instanceof UserTask) {
+ list.add((UserTask) flowElement);
+ }
+ }
+ }
+
+ /**
+ * 鑾峰彇娴佺▼鍏ㄩ儴鑺傜偣
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ public static List<FlowElement> getFlowElements(String processDefinitionId) {
+ BpmnModel bpmnModel = PROCESS_ENGINE.getRepositoryService().getBpmnModel(processDefinitionId);
+ List<FlowElement> list = new ArrayList<>();
+ List<Process> processes = bpmnModel.getProcesses();
+ Collection<FlowElement> flowElements = processes.get(0).getFlowElements();
+ buildFlowElements(flowElements, list);
+ return list;
+ }
+
+ /**
+ * 閫掑綊鑾峰彇鎵�鏈夎妭鐐�
+ *
+ * @param flowElements 鑺傜偣淇℃伅
+ * @param list 闆嗗悎
+ */
+ private static void buildFlowElements(Collection<FlowElement> flowElements, List<FlowElement> list) {
+ for (FlowElement flowElement : flowElements) {
+ list.add(flowElement);
+ if (flowElement instanceof SubProcess) {
+ Collection<FlowElement> subFlowElements = ((SubProcess) flowElement).getFlowElements();
+ buildFlowElements(subFlowElements, list);
+ }
+ }
+ }
+
+ /**
+ * 鑾峰彇鍏ㄩ儴鎵╁睍淇℃伅
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ */
+ public static Map<String, List<ExtensionElement>> getExtensionElements(String processDefinitionId) {
+ Map<String, List<ExtensionElement>> map = new HashMap<>();
+ List<FlowElement> flowElements = getFlowElements(processDefinitionId);
+ for (FlowElement flowElement : flowElements) {
+ if (flowElement instanceof UserTask && CollUtil.isNotEmpty(flowElement.getExtensionElements())) {
+ map.putAll(flowElement.getExtensionElements());
+ }
+ }
+ return map;
+ }
+
+ /**
+ * 鑾峰彇鏌愪釜鑺傜偣鐨勬墿灞曚俊鎭�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ * @param flowElementId 鑺傜偣id
+ */
+ public static Map<String, List<ExtensionElement>> getExtensionElement(String processDefinitionId, String flowElementId) {
+ BpmnModel bpmnModel = PROCESS_ENGINE.getRepositoryService().getBpmnModel(processDefinitionId);
+ Process process = bpmnModel.getMainProcess();
+ FlowElement flowElement = process.getFlowElement(flowElementId);
+ return flowElement.getExtensionElements();
+ }
+
+ /**
+ * 鍒ゆ柇褰撳墠鑺傜偣鏄惁涓虹敤鎴蜂换鍔�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ * @param taskDefinitionKey 娴佺▼瀹氫箟id
+ */
+ public static boolean isUserTask(String processDefinitionId, String taskDefinitionKey) {
+ BpmnModel bpmnModel = PROCESS_ENGINE.getRepositoryService().getBpmnModel(processDefinitionId);
+ FlowNode flowNode = (FlowNode) bpmnModel.getFlowElement(taskDefinitionKey);
+ return flowNode instanceof UserTask;
+ }
+
+ /**
+ * 鑾峰彇鐢宠浜鸿妭鐐�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ * @return 缁撴灉
+ */
+ public static UserTask getApplyUserTask(String processDefinitionId) {
+ BpmnModel bpmnModel = PROCESS_ENGINE.getRepositoryService().getBpmnModel(processDefinitionId);
+ Collection<FlowElement> flowElements = bpmnModel.getMainProcess().getFlowElements();
+ List<StartEvent> startEventList = flowElements.stream().filter(StartEvent.class::isInstance).map(StartEvent.class::cast).collect(Collectors.toList());
+ StartEvent startEvent = startEventList.get(0);
+ List<SequenceFlow> outgoingFlows = startEvent.getOutgoingFlows();
+ FlowElement targetFlowElement = outgoingFlows.get(0).getTargetFlowElement();
+ return (UserTask) targetFlowElement;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/QueryUtils.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/QueryUtils.java
new file mode 100644
index 0000000..944d9d7
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/QueryUtils.java
@@ -0,0 +1,154 @@
+package org.dromara.workflow.utils;
+
+import cn.hutool.core.bean.BeanUtil;
+import lombok.AccessLevel;
+import lombok.NoArgsConstructor;
+import org.dromara.common.core.utils.SpringUtils;
+import org.dromara.common.tenant.helper.TenantHelper;
+import org.dromara.workflow.domain.vo.TaskVo;
+import org.flowable.engine.ProcessEngine;
+import org.flowable.engine.history.HistoricActivityInstanceQuery;
+import org.flowable.engine.history.HistoricProcessInstanceQuery;
+import org.flowable.engine.repository.DeploymentQuery;
+import org.flowable.engine.repository.ModelQuery;
+import org.flowable.engine.repository.ProcessDefinitionQuery;
+import org.flowable.engine.runtime.ProcessInstanceQuery;
+import org.flowable.task.api.Task;
+import org.flowable.task.api.TaskQuery;
+import org.flowable.task.api.history.HistoricTaskInstanceQuery;
+
+import java.util.Collection;
+import java.util.List;
+import java.util.Set;
+
+/**
+ * 鏌ヨ宸ュ叿
+ *
+ * @author Lion Li
+ */
+@NoArgsConstructor(access = AccessLevel.PRIVATE)
+public class QueryUtils {
+
+ private static final ProcessEngine PROCESS_ENGINE = SpringUtils.getBean(ProcessEngine.class);
+
+ public static ModelQuery modelQuery() {
+ ModelQuery query = PROCESS_ENGINE.getRepositoryService().createModelQuery();
+ if (TenantHelper.isEnable()) {
+ query.modelTenantId(TenantHelper.getTenantId());
+ }
+ return query;
+ }
+
+ public static ProcessDefinitionQuery definitionQuery() {
+ ProcessDefinitionQuery query = PROCESS_ENGINE.getRepositoryService().createProcessDefinitionQuery();
+ if (TenantHelper.isEnable()) {
+ query.processDefinitionTenantId(TenantHelper.getTenantId());
+ }
+ return query;
+ }
+
+ public static DeploymentQuery deploymentQuery() {
+ DeploymentQuery query = PROCESS_ENGINE.getRepositoryService().createDeploymentQuery();
+ if (TenantHelper.isEnable()) {
+ query.deploymentTenantId(TenantHelper.getTenantId());
+ }
+ return query;
+ }
+
+ public static DeploymentQuery deploymentQuery(String deploymentId) {
+ return deploymentQuery().deploymentId(deploymentId);
+ }
+
+ public static DeploymentQuery deploymentQuery(List<String> deploymentIds) {
+ return deploymentQuery().deploymentIds(deploymentIds);
+ }
+
+ public static HistoricTaskInstanceQuery hisTaskInstanceQuery() {
+ HistoricTaskInstanceQuery query = PROCESS_ENGINE.getHistoryService().createHistoricTaskInstanceQuery();
+ if (TenantHelper.isEnable()) {
+ query.taskTenantId(TenantHelper.getTenantId());
+ }
+ return query;
+ }
+
+ public static HistoricTaskInstanceQuery hisTaskInstanceQuery(String processInstanceId) {
+ return hisTaskInstanceQuery().processInstanceId(processInstanceId);
+ }
+
+ public static ProcessInstanceQuery instanceQuery() {
+ ProcessInstanceQuery query = PROCESS_ENGINE.getRuntimeService().createProcessInstanceQuery();
+ if (TenantHelper.isEnable()) {
+ query.processInstanceTenantId(TenantHelper.getTenantId());
+ }
+ return query;
+ }
+
+ public static ProcessInstanceQuery instanceQuery(String processInstanceId) {
+ return instanceQuery().processInstanceId(processInstanceId);
+ }
+
+ public static ProcessInstanceQuery instanceQuery(Set<String> processInstanceIds) {
+ return instanceQuery().processInstanceIds(processInstanceIds);
+ }
+
+ public static HistoricProcessInstanceQuery hisInstanceQuery() {
+ HistoricProcessInstanceQuery query = PROCESS_ENGINE.getHistoryService().createHistoricProcessInstanceQuery();
+ if (TenantHelper.isEnable()) {
+ query.processInstanceTenantId(TenantHelper.getTenantId());
+ }
+ return query;
+ }
+
+ public static HistoricProcessInstanceQuery hisInstanceQuery(String processInstanceId) {
+ return hisInstanceQuery().processInstanceId(processInstanceId);
+ }
+
+ public static HistoricProcessInstanceQuery hisInstanceQuery(Set<String> processInstanceIds) {
+ return hisInstanceQuery().processInstanceIds(processInstanceIds);
+ }
+
+ public static HistoricActivityInstanceQuery hisActivityInstanceQuery() {
+ HistoricActivityInstanceQuery query = PROCESS_ENGINE.getHistoryService().createHistoricActivityInstanceQuery();
+ if (TenantHelper.isEnable()) {
+ query.activityTenantId(TenantHelper.getTenantId());
+ }
+ return query;
+ }
+
+ public static HistoricActivityInstanceQuery hisActivityInstanceQuery(String processInstanceId) {
+ return hisActivityInstanceQuery().processInstanceId(processInstanceId);
+ }
+
+ public static TaskQuery taskQuery() {
+ TaskQuery query = PROCESS_ENGINE.getTaskService().createTaskQuery();
+ if (TenantHelper.isEnable()) {
+ query.taskTenantId(TenantHelper.getTenantId());
+ }
+ return query;
+ }
+
+ public static TaskQuery taskQuery(String processInstanceId) {
+ return taskQuery().processInstanceId(processInstanceId);
+ }
+
+ public static TaskQuery taskQuery(Collection<String> processInstanceIds) {
+ return taskQuery().processInstanceIdIn(processInstanceIds);
+ }
+
+ /**
+ * 鎸夌収浠诲姟id鏌ヨ褰撳墠浠诲姟
+ *
+ * @param taskId 浠诲姟id
+ */
+ public static TaskVo getTask(String taskId) {
+ Task task = PROCESS_ENGINE.getTaskService().createTaskQuery().taskId(taskId).singleResult();
+ if (task == null) {
+ return null;
+ }
+ TaskVo taskVo = BeanUtil.toBean(task, TaskVo.class);
+ taskVo.setMultiInstance(WorkflowUtils.isMultiInstance(task.getProcessDefinitionId(), task.getTaskDefinitionKey()) != null);
+ String businessStatus = WorkflowUtils.getBusinessStatus(taskVo.getProcessInstanceId());
+ taskVo.setBusinessStatus(businessStatus);
+ return taskVo;
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/WorkflowUtils.java b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/WorkflowUtils.java
new file mode 100644
index 0000000..f475f19
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/java/org/dromara/workflow/utils/WorkflowUtils.java
@@ -0,0 +1,343 @@
+package org.dromara.workflow.utils;
+
+import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.util.ObjectUtil;
+import cn.hutool.core.util.StrUtil;
+import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
+import lombok.AccessLevel;
+import lombok.NoArgsConstructor;
+import org.dromara.common.core.domain.dto.UserDTO;
+import org.dromara.common.core.service.UserService;
+import org.dromara.common.core.utils.SpringUtils;
+import org.dromara.common.core.utils.StreamUtils;
+import org.dromara.common.core.utils.StringUtils;
+import org.dromara.common.core.utils.reflect.ReflectUtils;
+import org.dromara.common.mail.utils.MailUtils;
+import org.dromara.common.tenant.helper.TenantHelper;
+import org.dromara.common.websocket.dto.WebSocketMessageDto;
+import org.dromara.common.websocket.utils.WebSocketUtils;
+import org.dromara.workflow.common.constant.FlowConstant;
+import org.dromara.workflow.common.enums.BusinessStatusEnum;
+import org.dromara.workflow.common.enums.MessageTypeEnum;
+import org.dromara.workflow.common.enums.TaskStatusEnum;
+import org.dromara.workflow.domain.ActHiProcinst;
+import org.dromara.workflow.domain.ActHiTaskinst;
+import org.dromara.workflow.domain.vo.MultiInstanceVo;
+import org.dromara.workflow.domain.vo.ParticipantVo;
+import org.dromara.workflow.domain.vo.ProcessInstanceVo;
+import org.dromara.workflow.flowable.cmd.UpdateHiTaskInstCmd;
+import org.dromara.workflow.mapper.ActHiTaskinstMapper;
+import org.dromara.workflow.service.IActHiProcinstService;
+import org.flowable.bpmn.model.BpmnModel;
+import org.flowable.bpmn.model.FlowNode;
+import org.flowable.common.engine.api.delegate.Expression;
+import org.flowable.engine.ProcessEngine;
+import org.flowable.engine.history.HistoricProcessInstance;
+import org.flowable.engine.impl.bpmn.behavior.ParallelMultiInstanceBehavior;
+import org.flowable.engine.impl.bpmn.behavior.SequentialMultiInstanceBehavior;
+import org.flowable.identitylink.api.history.HistoricIdentityLink;
+import org.flowable.task.api.Task;
+import org.flowable.task.api.history.HistoricTaskInstance;
+import org.flowable.task.service.impl.persistence.entity.TaskEntity;
+
+import java.util.*;
+
+import static org.dromara.workflow.common.constant.FlowConstant.PROCESS_INSTANCE_VO;
+
+/**
+ * 宸ヤ綔娴佸伐鍏�
+ *
+ * @author may
+ */
+@NoArgsConstructor(access = AccessLevel.PRIVATE)
+public class WorkflowUtils {
+
+ private static final ProcessEngine PROCESS_ENGINE = SpringUtils.getBean(ProcessEngine.class);
+ private static final UserService USER_SERVICE = SpringUtils.getBean(UserService.class);
+ private static final IActHiProcinstService ACT_HI_PROCINST_SERVICE = SpringUtils.getBean(IActHiProcinstService.class);
+ private static final ActHiTaskinstMapper ACT_HI_TASKINST_MAPPER = SpringUtils.getBean(ActHiTaskinstMapper.class);
+
+ /**
+ * 鍒涘缓涓�涓柊浠诲姟
+ *
+ * @param currentTask 鍙傛暟
+ */
+ public static TaskEntity createNewTask(Task currentTask) {
+ TaskEntity task = null;
+ if (ObjectUtil.isNotEmpty(currentTask)) {
+ task = (TaskEntity) PROCESS_ENGINE.getTaskService().newTask();
+ task.setCategory(currentTask.getCategory());
+ task.setDescription(currentTask.getDescription());
+ task.setAssignee(currentTask.getAssignee());
+ task.setName(currentTask.getName());
+ task.setProcessDefinitionId(currentTask.getProcessDefinitionId());
+ task.setProcessInstanceId(currentTask.getProcessInstanceId());
+ task.setTaskDefinitionKey(currentTask.getTaskDefinitionKey());
+ task.setPriority(currentTask.getPriority());
+ task.setCreateTime(new Date());
+ task.setTenantId(TenantHelper.getTenantId());
+ PROCESS_ENGINE.getTaskService().saveTask(task);
+ }
+ if (ObjectUtil.isNotNull(task)) {
+ UpdateHiTaskInstCmd updateHiTaskInstCmd = new UpdateHiTaskInstCmd(Collections.singletonList(task.getId()), task.getProcessDefinitionId(), task.getProcessInstanceId());
+ PROCESS_ENGINE.getManagementService().executeCommand(updateHiTaskInstCmd);
+ }
+ return task;
+ }
+
+ /**
+ * 鎶勯�佷换鍔�
+ *
+ * @param parentTaskList 鐖剁骇浠诲姟
+ * @param userIds 浜哄憳id
+ */
+ public static void createCopyTask(List<Task> parentTaskList, List<Long> userIds) {
+ List<Task> list = new ArrayList<>();
+ String tenantId = TenantHelper.getTenantId();
+ for (Task parentTask : parentTaskList) {
+ for (Long userId : userIds) {
+ TaskEntity newTask = (TaskEntity) PROCESS_ENGINE.getTaskService().newTask();
+ newTask.setParentTaskId(parentTask.getId());
+ newTask.setAssignee(userId.toString());
+ newTask.setName("銆愭妱閫併��-" + parentTask.getName());
+ newTask.setProcessDefinitionId(parentTask.getProcessDefinitionId());
+ newTask.setProcessInstanceId(parentTask.getProcessInstanceId());
+ newTask.setTaskDefinitionKey(parentTask.getTaskDefinitionKey());
+ newTask.setTenantId(tenantId);
+ list.add(newTask);
+ }
+ }
+ PROCESS_ENGINE.getTaskService().bulkSaveTasks(list);
+ if (CollUtil.isNotEmpty(list) && CollUtil.isNotEmpty(parentTaskList)) {
+ String processInstanceId = parentTaskList.get(0).getProcessInstanceId();
+ String processDefinitionId = parentTaskList.get(0).getProcessDefinitionId();
+ List<String> taskIds = StreamUtils.toList(list, Task::getId);
+ ActHiTaskinst actHiTaskinst = new ActHiTaskinst();
+ actHiTaskinst.setProcDefId(processDefinitionId);
+ actHiTaskinst.setProcInstId(processInstanceId);
+ actHiTaskinst.setScopeType(TaskStatusEnum.COPY.getStatus());
+ actHiTaskinst.setTenantId(tenantId);
+ LambdaUpdateWrapper<ActHiTaskinst> updateWrapper = new LambdaUpdateWrapper<>();
+ updateWrapper.in(ActHiTaskinst::getId, taskIds);
+ ACT_HI_TASKINST_MAPPER.update(actHiTaskinst, updateWrapper);
+ for (Task task : list) {
+ PROCESS_ENGINE.getTaskService().addComment(task.getId(), task.getProcessInstanceId(), TaskStatusEnum.COPY.getStatus(), StrUtil.EMPTY);
+ }
+ }
+ }
+
+ /**
+ * 鑾峰彇褰撳墠浠诲姟鍙備笌鑰�
+ *
+ * @param taskId 浠诲姟id
+ */
+ public static ParticipantVo getCurrentTaskParticipant(String taskId) {
+ ParticipantVo participantVo = new ParticipantVo();
+ List<HistoricIdentityLink> linksForTask = PROCESS_ENGINE.getHistoryService().getHistoricIdentityLinksForTask(taskId);
+ Task task = QueryUtils.taskQuery().taskId(taskId).singleResult();
+ if (task != null && CollUtil.isNotEmpty(linksForTask)) {
+ List<HistoricIdentityLink> groupList = StreamUtils.filter(linksForTask, e -> StringUtils.isNotBlank(e.getGroupId()));
+ if (CollUtil.isNotEmpty(groupList)) {
+ List<Long> groupIds = StreamUtils.toList(groupList, e -> Long.valueOf(e.getGroupId()));
+ List<Long> userIds = USER_SERVICE.selectUserIdsByRoleIds(groupIds);
+ if (CollUtil.isNotEmpty(userIds)) {
+ participantVo.setGroupIds(groupIds);
+ List<UserDTO> userList = USER_SERVICE.selectListByIds(userIds);
+ if (CollUtil.isNotEmpty(userList)) {
+ List<Long> userIdList = StreamUtils.toList(userList, UserDTO::getUserId);
+ List<String> nickNames = StreamUtils.toList(userList, UserDTO::getNickName);
+ participantVo.setCandidate(userIdList);
+ participantVo.setCandidateName(nickNames);
+ participantVo.setClaim(!StringUtils.isBlank(task.getAssignee()));
+ }
+ }
+ } else {
+ List<HistoricIdentityLink> candidateList = StreamUtils.filter(linksForTask, e -> FlowConstant.CANDIDATE.equals(e.getType()));
+ List<Long> userIdList = new ArrayList<>();
+ for (HistoricIdentityLink historicIdentityLink : linksForTask) {
+ try {
+ userIdList.add(Long.valueOf(historicIdentityLink.getUserId()));
+ } catch (NumberFormatException ignored) {
+
+ }
+ }
+ List<UserDTO> userList = USER_SERVICE.selectListByIds(userIdList);
+ if (CollUtil.isNotEmpty(userList)) {
+ List<Long> userIds = StreamUtils.toList(userList, UserDTO::getUserId);
+ List<String> nickNames = StreamUtils.toList(userList, UserDTO::getNickName);
+ participantVo.setCandidate(userIds);
+ participantVo.setCandidateName(nickNames);
+ // 鍒ゆ柇褰撳墠浠诲姟鏄惁鍏锋湁澶氫釜鍔炵悊浜�
+ if (CollUtil.isNotEmpty(candidateList) && candidateList.size() > 1) {
+ // 濡傛灉 assignee 瀛樺湪锛屽垯璁剧疆褰撳墠浠诲姟宸茬粡琚棰�
+ participantVo.setClaim(StringUtils.isNotBlank(task.getAssignee()));
+ }
+ }
+ }
+ }
+ return participantVo;
+ }
+
+ /**
+ * 鍒ゆ柇褰撳墠鑺傜偣鏄惁涓轰細绛捐妭鐐�
+ *
+ * @param processDefinitionId 娴佺▼瀹氫箟id
+ * @param taskDefinitionKey 娴佺▼瀹氫箟id
+ */
+ public static MultiInstanceVo isMultiInstance(String processDefinitionId, String taskDefinitionKey) {
+ BpmnModel bpmnModel = PROCESS_ENGINE.getRepositoryService().getBpmnModel(processDefinitionId);
+ FlowNode flowNode = (FlowNode) bpmnModel.getFlowElement(taskDefinitionKey);
+ MultiInstanceVo multiInstanceVo = new MultiInstanceVo();
+ //鍒ゆ柇鏄惁涓哄苟琛屼細绛捐妭鐐�
+ if (flowNode.getBehavior() instanceof ParallelMultiInstanceBehavior behavior && behavior.getCollectionExpression() != null) {
+ Expression collectionExpression = behavior.getCollectionExpression();
+ String assigneeList = collectionExpression.getExpressionText();
+ String assignee = behavior.getCollectionElementVariable();
+ multiInstanceVo.setType(behavior);
+ multiInstanceVo.setAssignee(assignee);
+ multiInstanceVo.setAssigneeList(assigneeList);
+ return multiInstanceVo;
+ //鍒ゆ柇鏄惁涓轰覆琛屼細绛捐妭鐐�
+ } else if (flowNode.getBehavior() instanceof SequentialMultiInstanceBehavior behavior && behavior.getCollectionExpression() != null) {
+ Expression collectionExpression = behavior.getCollectionExpression();
+ String assigneeList = collectionExpression.getExpressionText();
+ String assignee = behavior.getCollectionElementVariable();
+ multiInstanceVo.setType(behavior);
+ multiInstanceVo.setAssignee(assignee);
+ multiInstanceVo.setAssigneeList(assigneeList);
+ return multiInstanceVo;
+ }
+ return null;
+ }
+
+ /**
+ * 鑾峰彇褰撳墠娴佺▼鐘舵��
+ *
+ * @param taskId 浠诲姟id
+ */
+ public static String getBusinessStatusByTaskId(String taskId) {
+ HistoricTaskInstance historicTaskInstance = QueryUtils.hisTaskInstanceQuery().taskId(taskId).singleResult();
+ HistoricProcessInstance historicProcessInstance = QueryUtils.hisInstanceQuery(historicTaskInstance.getProcessInstanceId()).singleResult();
+ return historicProcessInstance.getBusinessStatus();
+ }
+
+ /**
+ * 鑾峰彇褰撳墠娴佺▼鐘舵��
+ *
+ * @param processInstanceId 娴佺▼瀹炰緥id
+ */
+ public static String getBusinessStatus(String processInstanceId) {
+ HistoricProcessInstance historicProcessInstance = QueryUtils.hisInstanceQuery(processInstanceId).singleResult();
+ return historicProcessInstance.getBusinessStatus();
+ }
+
+ /**
+ * 璁剧疆娴佺▼瀹炰緥瀵硅薄
+ *
+ * @param obj 涓氬姟瀵硅薄
+ * @param businessKey 涓氬姟id
+ */
+ public static void setProcessInstanceVo(Object obj, String businessKey) {
+ if (StringUtils.isBlank(businessKey) || obj == null) {
+ return;
+ }
+ ActHiProcinst actHiProcinst = ACT_HI_PROCINST_SERVICE.selectByBusinessKey(businessKey);
+ if (actHiProcinst == null) {
+ ProcessInstanceVo processInstanceVo = new ProcessInstanceVo();
+ processInstanceVo.setBusinessStatus(BusinessStatusEnum.DRAFT.getStatus());
+ ReflectUtils.invokeSetter(obj, PROCESS_INSTANCE_VO, processInstanceVo);
+ return;
+ }
+ ProcessInstanceVo processInstanceVo = BeanUtil.toBean(actHiProcinst, ProcessInstanceVo.class);
+ processInstanceVo.setBusinessStatusName(BusinessStatusEnum.findByStatus(processInstanceVo.getBusinessStatus()));
+ ReflectUtils.invokeSetter(obj, PROCESS_INSTANCE_VO, processInstanceVo);
+ }
+
+ /**
+ * 璁剧疆娴佺▼瀹炰緥瀵硅薄
+ *
+ * @param obj 涓氬姟瀵硅薄
+ * @param idList 涓氬姟id
+ * @param fieldName 涓婚敭灞炴�у悕绉�
+ */
+ public static void setProcessInstanceListVo(Object obj, List<String> idList, String fieldName) {
+ if (CollUtil.isEmpty(idList) || obj == null) {
+ return;
+ }
+ List<ActHiProcinst> actHiProcinstList = ACT_HI_PROCINST_SERVICE.selectByBusinessKeyIn(idList);
+ if (obj instanceof Collection<?> collection) {
+ for (Object o : collection) {
+ String fieldValue = ReflectUtils.invokeGetter(o, fieldName).toString();
+ if (CollUtil.isEmpty(actHiProcinstList)) {
+ ProcessInstanceVo processInstanceVo = new ProcessInstanceVo();
+ processInstanceVo.setBusinessStatus(BusinessStatusEnum.DRAFT.getStatus());
+ processInstanceVo.setBusinessStatusName(BusinessStatusEnum.findByStatus(processInstanceVo.getBusinessStatus()));
+ ReflectUtils.invokeSetter(o, PROCESS_INSTANCE_VO, processInstanceVo);
+ } else {
+ ActHiProcinst actHiProcinst = actHiProcinstList.stream().filter(e -> e.getBusinessKey().equals(fieldValue)).findFirst().orElse(null);
+ if (ObjectUtil.isNotEmpty(actHiProcinst)) {
+ ProcessInstanceVo processInstanceVo = BeanUtil.toBean(actHiProcinst, ProcessInstanceVo.class);
+ processInstanceVo.setBusinessStatusName(BusinessStatusEnum.findByStatus(processInstanceVo.getBusinessStatus()));
+ ReflectUtils.invokeSetter(o, PROCESS_INSTANCE_VO, processInstanceVo);
+ } else {
+ ProcessInstanceVo processInstanceVo = new ProcessInstanceVo();
+ processInstanceVo.setBusinessStatus(BusinessStatusEnum.DRAFT.getStatus());
+ processInstanceVo.setBusinessStatusName(BusinessStatusEnum.findByStatus(processInstanceVo.getBusinessStatus()));
+ ReflectUtils.invokeSetter(o, PROCESS_INSTANCE_VO, processInstanceVo);
+ }
+ }
+ }
+ }
+ }
+
+ /**
+ * 鍙戦�佹秷鎭�
+ *
+ * @param list 浠诲姟
+ * @param name 娴佺▼鍚嶇О
+ * @param messageType 娑堟伅绫诲瀷
+ * @param message 娑堟伅鍐呭锛屼负绌哄垯鍙戦�侀粯璁ら厤缃殑娑堟伅鍐呭
+ */
+ public static void sendMessage(List<Task> list, String name, List<String> messageType, String message) {
+ Set<Long> userIds = new HashSet<>();
+ if (StringUtils.isBlank(message)) {
+ message = "鏈夋柊鐨勩��" + name + "銆戝崟鎹凡缁忔彁浜よ嚦鎮ㄧ殑寰呭姙锛岃鎮ㄥ強鏃跺鐞嗐��";
+ }
+ for (Task t : list) {
+ ParticipantVo taskParticipant = WorkflowUtils.getCurrentTaskParticipant(t.getId());
+ if (CollUtil.isNotEmpty(taskParticipant.getGroupIds())) {
+ List<Long> userIdList = USER_SERVICE.selectUserIdsByRoleIds(taskParticipant.getGroupIds());
+ if (CollUtil.isNotEmpty(userIdList)) {
+ userIds.addAll(userIdList);
+ }
+ }
+ List<Long> candidate = taskParticipant.getCandidate();
+ if (CollUtil.isNotEmpty(candidate)) {
+ userIds.addAll(candidate);
+ }
+ }
+ if (CollUtil.isNotEmpty(userIds)) {
+ List<UserDTO> userList = USER_SERVICE.selectListByIds(new ArrayList<>(userIds));
+ for (String code : messageType) {
+ MessageTypeEnum messageTypeEnum = MessageTypeEnum.getByCode(code);
+ if (ObjectUtil.isNotEmpty(messageTypeEnum)) {
+ switch (messageTypeEnum) {
+ case SYSTEM_MESSAGE:
+ WebSocketMessageDto dto = new WebSocketMessageDto();
+ dto.setSessionKeys(new ArrayList<>(userIds));
+ dto.setMessage(message);
+ WebSocketUtils.publishMessage(dto);
+ break;
+ case EMAIL_MESSAGE:
+ MailUtils.sendText(StreamUtils.join(userList, UserDTO::getEmail), "鍗曟嵁瀹℃壒鎻愰啋", message);
+ break;
+ case SMS_MESSAGE:
+ //todo 鐭俊鍙戦��
+ break;
+ }
+ }
+ }
+ }
+ }
+}
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/package-info.md b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/package-info.md
new file mode 100644
index 0000000..c938b1e
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/package-info.md
@@ -0,0 +1,3 @@
+java鍖呬娇鐢� `.` 鍒嗗壊 resource 鐩綍浣跨敤 `/` 鍒嗗壊
+<br>
+姝ゆ枃浠剁洰鐨� 闃叉鏂囦欢澶圭矘杩炴壘涓嶅埌 `xml` 鏂囦欢
\ No newline at end of file
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActHiProcinstMapper.xml b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActHiProcinstMapper.xml
new file mode 100644
index 0000000..dd05785
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActHiProcinstMapper.xml
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE mapper
+ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+ "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.dromara.workflow.mapper.ActHiProcinstMapper">
+
+</mapper>
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActHiTaskinstMapper.xml b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActHiTaskinstMapper.xml
new file mode 100644
index 0000000..7e73b60
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActHiTaskinstMapper.xml
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE mapper
+ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+ "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.dromara.workflow.mapper.ActHiTaskinstMapper">
+
+</mapper>
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActTaskMapper.xml b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActTaskMapper.xml
new file mode 100644
index 0000000..d1508ab
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/ActTaskMapper.xml
@@ -0,0 +1,78 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE mapper
+ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+ "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.dromara.workflow.mapper.ActTaskMapper">
+ <resultMap type="org.dromara.workflow.domain.vo.TaskVo" id="TaskVoResult">
+ <result property="id" column="ID_"/>
+ <result property="name" column="NAME_"/>
+ <result property="description" column="DESCRIPTION_"/>
+ <result property="priority" column="PRIORITY_"/>
+ <result property="owner" column="OWNER_"/>
+ <result property="assignee" column="ASSIGNEE_"/>
+ <result property="processInstanceId" column="PROC_INST_ID_"/>
+ <result property="executionId" column="EXECUTION_ID_"/>
+ <result property="taskDefinitionId" column="TASK_DEF_ID_"/>
+ <result property="processDefinitionId" column="PROC_DEF_ID_"/>
+ <result property="createTime" column="CREATE_TIME_"/>
+ <result property="startTime" column="START_TIME_"/>
+ <result property="endTime" column="END_TIME_"/>
+ <result property="taskDefinitionKey" column="TASK_DEF_KEY_"/>
+ <result property="dueDate" column="DUE_DATE_"/>
+ <result property="category" column="CATEGORY_"/>
+ <result property="parentTaskId" column="PARENT_TASK_ID_"/>
+ <result property="tenantId" column="TENANT_ID_"/>
+ <result property="claimTime" column="CLAIM_TIME"/>
+ <result property="businessStatus" column="BUSINESS_STATUS_"/>
+ <result property="processDefinitionName" column="processDefinitionName"/>
+ <result property="processDefinitionKey" column="processDefinitionKey"/>
+ <result property="processDefinitionVersion" column="processDefinitionVersion"/>
+ <result property="businessKey" column="BUSINESS_KEY_"/>
+
+ </resultMap>
+ <select id="getTaskWaitByPage" resultMap="TaskVoResult">
+ select *
+ from (SELECT RES.*,
+ AHP.BUSINESS_STATUS_,
+ AHP.BUSINESS_KEY_,
+ ARP.NAME_ AS processDefinitionName,
+ ARP.KEY_ AS processDefinitionKey,
+ ARP.VERSION_ AS processDefinitionVersion
+ FROM ACT_RU_TASK RES
+ INNER JOIN ACT_HI_PROCINST AHP ON RES.PROC_INST_ID_ = AHP.PROC_INST_ID_
+ INNER JOIN ACT_RE_PROCDEF ARP ON ARP.ID_ = RES.PROC_DEF_ID_
+ WHERE RES.PARENT_TASK_ID_ IS NULL
+ ORDER BY RES.CREATE_TIME_ DESC) t ${ew.getCustomSqlSegment}
+ </select>
+
+ <select id="getTaskFinishByPage" resultMap="TaskVoResult">
+ select *
+ from (SELECT HTI.*,
+ AHP.BUSINESS_STATUS_,
+ AHP.BUSINESS_KEY_,
+ ARP.NAME_ AS processDefinitionName,
+ ARP.KEY_ AS processDefinitionKey,
+ ARP.VERSION_ AS processDefinitionVersion
+ FROM ACT_HI_TASKINST HTI
+ INNER JOIN ACT_HI_PROCINST AHP ON HTI.PROC_INST_ID_ = AHP.PROC_INST_ID_
+ INNER JOIN ACT_RE_PROCDEF ARP ON ARP.ID_ = HTI.PROC_DEF_ID_
+ WHERE HTI.PARENT_TASK_ID_ IS NULL AND HTI.END_TIME_ IS NOT NULL
+ ORDER BY HTI.START_TIME_ DESC) t ${ew.getCustomSqlSegment}
+ </select>
+
+ <select id="getTaskCopyByPage" resultMap="TaskVoResult">
+ select *
+ from (SELECT AHT.*,
+ AHP.BUSINESS_STATUS_,
+ AHP.BUSINESS_KEY_,
+ ARP.NAME_ as processDefinitionName,
+ ARP.KEY_ as processDefinitionKey,
+ ARP.VERSION_ AS processDefinitionVersion
+ FROM ACT_HI_TASKINST AHT
+ INNER JOIN ACT_HI_PROCINST AHP ON AHT.PROC_INST_ID_ = AHP.PROC_INST_ID_
+ INNER JOIN ACT_RE_PROCDEF ARP ON ARP.ID_ = AHT.PROC_DEF_ID_
+ WHERE AHT.PARENT_TASK_ID_ IS NOT NULL
+ and AHT.scope_type_ = 'copy'
+ ORDER BY AHT.START_TIME_ DESC) t ${ew.getCustomSqlSegment}
+ </select>
+</mapper>
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/TestLeaveMapper.xml b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/TestLeaveMapper.xml
new file mode 100644
index 0000000..d52f6b0
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/TestLeaveMapper.xml
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE mapper
+ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+ "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.dromara.workflow.mapper.TestLeaveMapper">
+
+</mapper>
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfCategoryMapper.xml b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfCategoryMapper.xml
new file mode 100644
index 0000000..4375cb2
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfCategoryMapper.xml
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE mapper
+ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+ "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.dromara.workflow.mapper.WfCategoryMapper">
+
+</mapper>
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfDefinitionConfigMapper.xml b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfDefinitionConfigMapper.xml
new file mode 100644
index 0000000..8d579f7
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfDefinitionConfigMapper.xml
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE mapper
+ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+ "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.dromara.workflow.mapper.WfDefinitionConfigMapper">
+
+</mapper>
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfFormManageMapper.xml b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfFormManageMapper.xml
new file mode 100644
index 0000000..59221f8
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfFormManageMapper.xml
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE mapper
+ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+ "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.dromara.workflow.mapper.WfFormManageMapper">
+
+</mapper>
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfNodeConfigMapper.xml b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfNodeConfigMapper.xml
new file mode 100644
index 0000000..b65194f
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfNodeConfigMapper.xml
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE mapper
+ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+ "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.dromara.workflow.mapper.WfNodeConfigMapper">
+
+</mapper>
diff --git a/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfTaskBackNodeMapper.xml b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfTaskBackNodeMapper.xml
new file mode 100644
index 0000000..4a9179b
--- /dev/null
+++ b/ruoyi-modules/ruoyi-workflow/src/main/resources/mapper/workflow/WfTaskBackNodeMapper.xml
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE mapper
+ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+ "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.dromara.workflow.mapper.WfTaskBackNodeMapper">
+
+</mapper>
diff --git a/script/bin/ry.bat b/script/bin/ry.bat
index d214af4..ea98cbe 100644
--- a/script/bin/ry.bat
+++ b/script/bin/ry.bat
@@ -5,7 +5,7 @@
set AppName=ruoyi-admin.jar
rem JVM鍙傛暟
-set JVM_OPTS="-Dname=%AppName% -Duser.timezone=Asia/Shanghai -Xms512m -Xmx1024m -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=512m -XX:+HeapDumpOnOutOfMemoryError -Xlog:gc*,:time,tags,level -XX:+UseZGC"
+set JVM_OPTS="-Dname=%AppName% -Duser.timezone=Asia/Shanghai -Xms512m -Xmx1024m -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=512m -XX:+HeapDumpOnOutOfMemoryError -XX:+UseZGC"
ECHO.
diff --git a/script/bin/ry.sh b/script/bin/ry.sh
index 0df25e7..a6f5d9c 100644
--- a/script/bin/ry.sh
+++ b/script/bin/ry.sh
@@ -3,7 +3,7 @@
AppName=ruoyi-admin.jar
# JVM鍙傛暟
-JVM_OPTS="-Dname=$AppName -Duser.timezone=Asia/Shanghai -Xms512m -Xmx1024m -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=512m -XX:+HeapDumpOnOutOfMemoryError -Xlog:gc*,:time,tags,level -XX:+UseZGC"
+JVM_OPTS="-Dname=$AppName -Duser.timezone=Asia/Shanghai -Xms512m -Xmx1024m -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=512m -XX:+HeapDumpOnOutOfMemoryError -XX:+UseZGC"
APP_HOME=`pwd`
LOG_PATH=$APP_HOME/logs/$AppName.log
diff --git "a/script/bpmn/\346\250\241\345\236\213.zip" "b/script/bpmn/\346\250\241\345\236\213.zip"
new file mode 100644
index 0000000..d886e0f
--- /dev/null
+++ "b/script/bpmn/\346\250\241\345\236\213.zip"
Binary files differ
diff --git a/script/docker/docker-compose.yml b/script/docker/docker-compose.yml
index 63d819e..97024a0 100644
--- a/script/docker/docker-compose.yml
+++ b/script/docker/docker-compose.yml
@@ -100,7 +100,7 @@
network_mode: "host"
ruoyi-server1:
- image: ruoyi/ruoyi-server:5.1.2
+ image: ruoyi/ruoyi-server:5.2.0
container_name: ruoyi-server1
environment:
# 鏃跺尯涓婃捣
@@ -115,7 +115,7 @@
network_mode: "host"
ruoyi-server2:
- image: ruoyi/ruoyi-server:5.1.2
+ image: ruoyi/ruoyi-server:5.2.0
container_name: ruoyi-server2
environment:
# 鏃跺尯涓婃捣
@@ -130,7 +130,7 @@
network_mode: "host"
ruoyi-monitor-admin:
- image: ruoyi/ruoyi-monitor-admin:5.1.2
+ image: ruoyi/ruoyi-monitor-admin:5.2.0
container_name: ruoyi-monitor-admin
environment:
# 鏃跺尯涓婃捣
@@ -141,18 +141,16 @@
privileged: true
network_mode: "host"
- ruoyi-powerjob-server:
- image: ruoyi/ruoyi-powerjob-server:5.1.2
- container_name: ruoyi-powerjob-server
+ ruoyi-snailjob-server:
+ image: ruoyi/ruoyi-snailjob-server:5.2.0
+ container_name: ruoyi-snailjob-server
environment:
# 鏃跺尯涓婃捣
TZ: Asia/Shanghai
ports:
- - "7700:7700"
- - "10086:10086"
- - "10010:10010"
+ - "8800:8800"
+ - "1788:1788"
volumes:
- - /docker/powerjob/logs/:/ruoyi/powerjob/logs
+ - /docker/snailjob/logs/:/ruoyi/snailjob/logs
privileged: true
network_mode: "host"
-
diff --git a/script/docker/nginx/conf/nginx.conf b/script/docker/nginx/conf/nginx.conf
index 2aa6587..dcc4525 100644
--- a/script/docker/nginx/conf/nginx.conf
+++ b/script/docker/nginx/conf/nginx.conf
@@ -31,8 +31,8 @@
server 127.0.0.1:9090;
}
- upstream powerjob-server {
- server 127.0.0.1:7700;
+ upstream snailjob-server {
+ server 127.0.0.1:8800;
}
server {
@@ -96,20 +96,12 @@
proxy_pass http://monitor-admin/admin/;
}
- # https 浼氭嫤鎴唴閾炬墍鏈夌殑 http 璇锋眰 閫犳垚鍔熻兘鏃犳硶浣跨敤
- # 瑙e喅鏂规1 灏� powerjob 鏈嶅姟 涔熼厤缃垚 https
- # 瑙e喅鏂规2 灏嗚彍鍗曢厤缃负澶栭摼璁块棶 璧扮嫭绔嬮〉闈� http 璁块棶
- location /powerjob/ {
+ location /snail-job/ {
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header REMOTE-HOST $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
- proxy_pass http://powerjob-server/;
- }
-
- # 瑙e喅 powerjob 浠g悊涔嬪悗闈欐�佹枃浠舵棤娉曡闂殑闂 璇峰嬁淇敼涔卞姩
- location ~ ^/(js|css|jpg|png|svg|woff|ttf|ico|img)/ {
- proxy_pass http://powerjob-server;
+ proxy_pass http://snailjob-server/snail-job/;
}
error_page 500 502 503 504 /50x.html;
diff --git a/script/sql/flowable.sql b/script/sql/flowable.sql
new file mode 100644
index 0000000..c3f7428
--- /dev/null
+++ b/script/sql/flowable.sql
@@ -0,0 +1,175 @@
+insert into sys_menu values('11616', '宸ヤ綔娴�' , '0', '6', 'workflow', '', '', '1', '0', 'M', '0', '0', '', 'workflow', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11617', '妯″瀷绠$悊', '11616', '2', 'model', 'workflow/model/index', '', '1', '1', 'C', '0', '0', 'workflow:model:list', 'model', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11618', '鎴戠殑浠诲姟', '0', '7', 'task', '', '', '1', '0', 'M', '0', '0', '', 'my-task', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11619', '鎴戠殑寰呭姙', '11618', '2', 'taskWaiting', 'workflow/task/taskWaiting', '', '1', '1', 'C', '0', '0', '', 'waiting', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11632', '鎴戠殑宸插姙', '11618', '3', 'taskFinish', 'workflow/task/taskFinish', '', '1', '1', 'C', '0', '0', '', 'finish', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11633', '鎴戠殑鎶勯��', '11618', '4', 'taskCopyList', 'workflow/task/taskCopyList', '', '1', '1', 'C', '0', '0', '', 'my-copy', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11620', '娴佺▼瀹氫箟', '11616', '3', 'processDefinition', 'workflow/processDefinition/index', '', '1', '1', 'C', '0', '0', '', 'process-definition', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11621', '娴佺▼瀹炰緥', '11630', '1', 'processInstance', 'workflow/processInstance/index', '', '1', '1', 'C', '0', '0', '', 'tree-table', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11622', '娴佺▼鍒嗙被', '11616', '1', 'category', 'workflow/category/index', '', '1', '0', 'C', '0', '0', 'workflow:category:list', 'category', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11629', '鎴戝彂璧风殑', '11618', '1', 'myDocument', 'workflow/task/myDocument', '', '1', '1', 'C', '0', '0', '', 'guide', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11630', '娴佺▼鐩戞帶', '11616', '4', 'monitor', '', '', '1', '0', 'M', '0', '0', '', 'monitor', 103, 1, sysdate(), NULL, NULL, '');
+insert into sys_menu values('11631', '寰呭姙浠诲姟', '11630', '2', 'allTaskWaiting', 'workflow/task/allTaskWaiting', '', '1', '1', 'C', '0', '0', '', 'waiting', 103, 1, sysdate(), NULL, NULL, '');
+
+
+-- 娴佺▼鍒嗙被绠$悊鐩稿叧鎸夐挳
+insert into sys_menu values ('11623', '娴佺▼鍒嗙被鏌ヨ', '11622', '1', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:query', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values ('11624', '娴佺▼鍒嗙被鏂板', '11622', '2', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:add', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values ('11625', '娴佺▼鍒嗙被淇敼', '11622', '3', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:edit', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values ('11626', '娴佺▼鍒嗙被鍒犻櫎', '11622', '4', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:remove','#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values ('11627', '娴佺▼鍒嗙被瀵煎嚭', '11622', '5', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:export','#', 103, 1, sysdate(), null, null, '');
+-- 璇峰亣鍗曚俊鎭�
+create table test_leave
+(
+ id bigint not null comment '涓婚敭',
+ leave_type varchar(255) not null comment '璇峰亣绫诲瀷',
+ start_date datetime not null comment '寮�濮嬫椂闂�',
+ end_date datetime not null comment '缁撴潫鏃堕棿',
+ leave_days int(10) not null comment '璇峰亣澶╂暟',
+ remark varchar(255) null comment '璇峰亣鍘熷洜',
+ create_dept bigint null comment '鍒涘缓閮ㄩ棬',
+ create_by bigint null comment '鍒涘缓鑰�',
+ create_time datetime null comment '鍒涘缓鏃堕棿',
+ update_by bigint null comment '鏇存柊鑰�',
+ update_time datetime null comment '鏇存柊鏃堕棿',
+ tenant_id varchar(20) null comment '绉熸埛缂栧彿',
+ PRIMARY KEY (id) USING BTREE
+) ENGINE = InnoDB COMMENT = '璇峰亣鐢宠琛�';
+
+-- 娴佺▼鍒嗙被淇℃伅琛�
+create table wf_category
+(
+ id bigint not null comment '涓婚敭'
+ primary key,
+ category_name varchar(255) null comment '鍒嗙被鍚嶇О',
+ category_code varchar(255) null comment '鍒嗙被缂栫爜',
+ parent_id bigint null comment '鐖剁骇id',
+ sort_num int(19) null comment '鎺掑簭',
+ tenant_id varchar(20) null comment '绉熸埛缂栧彿',
+ create_dept bigint null comment '鍒涘缓閮ㄩ棬',
+ create_by bigint null comment '鍒涘缓鑰�',
+ create_time datetime null comment '鍒涘缓鏃堕棿',
+ update_by bigint null comment '鏇存柊鑰�',
+ update_time datetime null comment '鏇存柊鏃堕棿',
+ constraint uni_category_code
+ unique (category_code)
+) engine=innodb comment= '娴佺▼鍒嗙被';
+INSERT INTO wf_category values (1, 'OA', 'OA', 0, 0, '000000', 103, 1, sysdate(), 1, sysdate());
+
+create table wf_task_back_node
+(
+ id bigint not null
+ primary key,
+ node_id varchar(255) not null comment '鑺傜偣id',
+ node_name varchar(255) not null comment '鑺傜偣鍚嶇О',
+ order_no int not null comment '鎺掑簭',
+ instance_id varchar(255) null comment '娴佺▼瀹炰緥id',
+ task_type varchar(255) not null comment '鑺傜偣绫诲瀷',
+ assignee varchar(2000) not null comment '瀹℃壒浜�',
+ tenant_id varchar(20) null comment '绉熸埛缂栧彿',
+ create_dept bigint null comment '鍒涘缓閮ㄩ棬',
+ create_by bigint null comment '鍒涘缓鑰�',
+ create_time datetime null comment '鍒涘缓鏃堕棿',
+ update_by bigint null comment '鏇存柊鑰�',
+ update_time datetime null comment '鏇存柊鏃堕棿'
+)
+ comment '鑺傜偣瀹℃壒璁板綍';
+
+create table wf_definition_config
+(
+ id bigint not null comment '涓婚敭'
+ primary key,
+ table_name varchar(255) not null comment '琛ㄥ悕',
+ definition_id varchar(255) not null comment '娴佺▼瀹氫箟ID',
+ process_key varchar(255) not null comment '娴佺▼KEY',
+ version int(10) not null comment '娴佺▼鐗堟湰',
+ create_dept bigint null comment '鍒涘缓閮ㄩ棬',
+ create_by bigint null comment '鍒涘缓鑰�',
+ create_time datetime null comment '鍒涘缓鏃堕棿',
+ update_by bigint null comment '鏇存柊鑰�',
+ update_time datetime null comment '鏇存柊鏃堕棿',
+ remark varchar(500) default '' null comment '澶囨敞',
+ tenant_id varchar(20) null comment '绉熸埛缂栧彿',
+ constraint uni_definition_id
+ unique (definition_id)
+)
+ comment '娴佺▼瀹氫箟閰嶇疆';
+
+create table wf_form_manage
+(
+ id bigint not null comment '涓婚敭'
+ primary key,
+ form_name varchar(255) not null comment '琛ㄥ崟鍚嶇О',
+ form_type varchar(255) not null comment '琛ㄥ崟绫诲瀷',
+ router varchar(255) not null comment '璺敱鍦板潃/琛ㄥ崟ID',
+ remark varchar(500) null comment '澶囨敞',
+ tenant_id varchar(20) null comment '绉熸埛缂栧彿',
+ create_dept bigint null comment '鍒涘缓閮ㄩ棬',
+ create_by bigint null comment '鍒涘缓鑰�',
+ create_time datetime null comment '鍒涘缓鏃堕棿',
+ update_by bigint null comment '鏇存柊鑰�',
+ update_time datetime null comment '鏇存柊鏃堕棿'
+)
+ comment '琛ㄥ崟绠$悊';
+
+insert into wf_form_manage(id, form_name, form_type, router, remark, tenant_id, create_dept, create_by, create_time, update_by, update_time) VALUES (1, '璇峰亣鐢宠', 'static', '/demo/leaveEdit/index', NULL, '000000', 103, 1, sysdate(), 1, sysdate());
+
+create table wf_node_config
+(
+ id bigint not null comment '涓婚敭'
+ primary key,
+ form_id bigint null comment '琛ㄥ崟id',
+ form_type varchar(255) null comment '琛ㄥ崟绫诲瀷',
+ node_name varchar(255) not null comment '鑺傜偣鍚嶇О',
+ node_id varchar(255) not null comment '鑺傜偣id',
+ definition_id varchar(255) not null comment '娴佺▼瀹氫箟id',
+ apply_user_task char(1) default '0' comment '鏄惁涓虹敵璇蜂汉鑺傜偣 锛�0鏄� 1鍚︼級',
+ create_dept bigint null comment '鍒涘缓閮ㄩ棬',
+ create_by bigint null comment '鍒涘缓鑰�',
+ create_time datetime null comment '鍒涘缓鏃堕棿',
+ update_by bigint null comment '鏇存柊鑰�',
+ update_time datetime null comment '鏇存柊鏃堕棿',
+ tenant_id varchar(20) null comment '绉熸埛缂栧彿'
+)
+ comment '鑺傜偣閰嶇疆';
+
+
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11638, '璇峰亣鐢宠', 5, 1, 'leave', 'workflow/leave/index', 1, 0, 'C', '0', '0', 'demo:leave:list', '#', 103, 1, sysdate(), NULL, NULL, '璇峰亣鐢宠鑿滃崟');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11639, '璇峰亣鐢宠鏌ヨ', 11638, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:query', '#', 103, 1, sysdate(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11640, '璇峰亣鐢宠鏂板', 11638, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:add', '#', 103, 1, sysdate(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11641, '璇峰亣鐢宠淇敼', 11638, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:edit', '#', 103, 1, sysdate(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11642, '璇峰亣鐢宠鍒犻櫎', 11638, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:remove', '#', 103, 1, sysdate(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11643, '璇峰亣鐢宠瀵煎嚭', 11638, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:export', '#', 103, 1, sysdate(), NULL, NULL, '');
+
+INSERT INTO sys_dict_type(dict_id, tenant_id, dict_name, dict_type, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (13, '000000', '涓氬姟鐘舵��', 'wf_business_status', 103, 1, sysdate(), NULL, NULL, '涓氬姟鐘舵�佸垪琛�');
+INSERT INTO sys_dict_type(dict_id, tenant_id, dict_name, dict_type, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (14, '000000', '琛ㄥ崟绫诲瀷', 'wf_form_type', 103, 1, sysdate(), NULL, NULL, '琛ㄥ崟绫诲瀷鍒楄〃');
+
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (39, '000000', 1, '宸叉挙閿�', 'cancel', 'wf_business_status', '', 'danger', 'N', 103, 1, sysdate(), NULL, NULL, '宸叉挙閿�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (40, '000000', 2, '鑽夌', 'draft', 'wf_business_status', '', 'info', 'N', 103, 1, sysdate(), NULL, NULL, '鑽夌');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (41, '000000', 3, '寰呭鏍�', 'waiting', 'wf_business_status', '', 'primary', 'N', 103, 1,sysdate(), NULL, NULL, '寰呭鏍�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (42, '000000', 4, '宸插畬鎴�', 'finish', 'wf_business_status', '', 'success', 'N', 103, 1, sysdate(), NULL, NULL, '宸插畬鎴�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (43, '000000', 5, '宸蹭綔搴�', 'invalid', 'wf_business_status', '', 'danger', 'N', 103, 1, sysdate(), NULL, NULL, '宸蹭綔搴�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (44, '000000', 6, '宸查��鍥�', 'back', 'wf_business_status', '', 'danger', 'N', 103, 1, sysdate(), NULL, NULL, '宸查��鍥�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (45, '000000', 7, '宸茬粓姝�', 'termination', 'wf_business_status', '', 'danger', 'N', 103, 1,sysdate(), NULL, NULL, '宸茬粓姝�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (46, '000000', 1, '鑷畾涔夎〃鍗�', 'static', 'wf_form_type', '', 'success', 'N', 103, 1, sysdate(), NULL, NULL, '鑷畾涔夎〃鍗�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (47, '000000', 2, '鍔ㄦ�佽〃鍗�', 'dynamic', 'wf_form_type', '', 'primary', 'N', 103, 1, sysdate(), NULL, NULL, '鍔ㄦ�佽〃鍗�');
+
+-- 琛ㄥ崟绠$悊 SQL
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11628, '琛ㄥ崟绠$悊', '11616', '5', 'formManage', 'workflow/formManage/index', 1, 0, 'C', '0', '0', 'workflow:formManage:list', 'tree-table', 103, 1, sysdate(), null, null, '琛ㄥ崟绠$悊鑿滃崟');
+
+-- 琛ㄥ崟绠$悊鎸夐挳 SQL
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11644, '琛ㄥ崟绠$悊鏌ヨ', 11628, '1', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:query', '', 103, 1, sysdate(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11645, '琛ㄥ崟绠$悊鏂板', 11628, '2', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:add', '', 103, 1, sysdate(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11646, '琛ㄥ崟绠$悊淇敼', 11628, '3', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:edit', '', 103, 1, sysdate(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11647, '琛ㄥ崟绠$悊鍒犻櫎', 11628, '4', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:remove', '', 103, 1, sysdate(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11648, '琛ㄥ崟绠$悊瀵煎嚭', 11628, '5', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:export', 'tree-table', 103, 1, sysdate(), null, null, '');
diff --git a/script/sql/oracle/flowable.sql b/script/sql/oracle/flowable.sql
new file mode 100644
index 0000000..afd5c0b
--- /dev/null
+++ b/script/sql/oracle/flowable.sql
@@ -0,0 +1,259 @@
+insert into sys_menu values('11616', '宸ヤ綔娴�' , '0', '6', 'workflow', '', '', '1', '0', 'M', '0', '0', '', 'workflow', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11617', '妯″瀷绠$悊', '11616', '2', 'model', 'workflow/model/index', '', '1', '1', 'C', '0', '0', 'workflow:model:list', 'model', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11618', '鎴戠殑浠诲姟', '0', '7', 'task', '', '', '1', '0', 'M', '0', '0', '', 'my-task', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11619', '鎴戠殑寰呭姙', '11618', '2', 'taskWaiting', 'workflow/task/taskWaiting', '', '1', '1', 'C', '0', '0', '', 'waiting', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11632', '鎴戠殑宸插姙', '11618', '3', 'taskFinish', 'workflow/task/taskFinish', '', '1', '1', 'C', '0', '0', '', 'finish', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11633', '鎴戠殑鎶勯��', '11618', '4', 'taskCopyList', 'workflow/task/taskCopyList', '', '1', '1', 'C', '0', '0', '', 'my-copy', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11620', '娴佺▼瀹氫箟', '11616', '3', 'processDefinition', 'workflow/processDefinition/index', '', '1', '1', 'C', '0', '0', '', 'process-definition', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11621', '娴佺▼瀹炰緥', '11630', '1', 'processInstance', 'workflow/processInstance/index', '', '1', '1', 'C', '0', '0', '', 'tree-table', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11622', '娴佺▼鍒嗙被', '11616', '1', 'category', 'workflow/category/index', '', '1', '0', 'C', '0', '0', 'workflow:category:list', 'category', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11629', '鎴戝彂璧风殑', '11618', '1', 'myDocument', 'workflow/task/myDocument', '', '1', '1', 'C', '0', '0', '', 'guide', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11630', '娴佺▼鐩戞帶', '11616', '4', 'monitor', '', '', '1', '0', 'M', '0', '0', '', 'monitor', 103, 1, sysdate, NULL, NULL, '');
+insert into sys_menu values('11631', '寰呭姙浠诲姟', '11630', '2', 'allTaskWaiting', 'workflow/task/allTaskWaiting', '', '1', '1', 'C', '0', '0', '', 'waiting', 103, 1, sysdate, NULL, NULL, '');
+
+
+-- 娴佺▼鍒嗙被绠$悊鐩稿叧鎸夐挳
+insert into sys_menu values ('11623', '娴佺▼鍒嗙被鏌ヨ', '11622', '1', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:query', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values ('11624', '娴佺▼鍒嗙被鏂板', '11622', '2', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:add', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values ('11625', '娴佺▼鍒嗙被淇敼', '11622', '3', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:edit', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values ('11626', '娴佺▼鍒嗙被鍒犻櫎', '11622', '4', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:remove','#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values ('11627', '娴佺▼鍒嗙被瀵煎嚭', '11622', '5', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:export','#', 103, 1, sysdate, null, null, '');
+
+-- 璇峰亣鍗曚俊鎭�
+create table TEST_LEAVE
+(
+ ID NUMBER(20) not null
+ constraint PK_TEST_LEAVE
+ primary key,
+ LEAVE_TYPE VARCHAR2(255),
+ START_DATE DATE,
+ END_DATE DATE,
+ LEAVE_DAYS NUMBER(10),
+ REMARK VARCHAR2(255),
+ CREATE_DEPT NUMBER(20),
+ CREATE_BY NUMBER(20),
+ CREATE_TIME DATE,
+ UPDATE_BY NUMBER(20),
+ UPDATE_TIME DATE,
+ TENANT_ID VARCHAR2(20)
+);
+
+comment on table TEST_LEAVE is '璇峰亣鐢宠琛�';
+comment on column TEST_LEAVE.ID is '涓婚敭';
+comment on column TEST_LEAVE.LEAVE_TYPE is '璇峰亣绫诲瀷';
+comment on column TEST_LEAVE.START_DATE is '寮�濮嬫椂闂�';
+comment on column TEST_LEAVE.END_DATE is '缁撴潫鏃堕棿';
+comment on column TEST_LEAVE.LEAVE_DAYS is '璇峰亣澶╂暟';
+comment on column TEST_LEAVE.REMARK is '璇峰亣鍘熷洜';
+comment on column TEST_LEAVE.CREATE_DEPT is '鍒涘缓閮ㄩ棬';
+comment on column TEST_LEAVE.CREATE_BY is '鍒涘缓鑰�';
+comment on column TEST_LEAVE.CREATE_TIME is '鍒涘缓鏃堕棿';
+comment on column TEST_LEAVE.UPDATE_BY is '鏇存柊鑰�';
+comment on column TEST_LEAVE.UPDATE_TIME is '鏇存柊鏃堕棿';
+comment on column TEST_LEAVE.TENANT_ID is '绉熸埛缂栧彿';
+
+-- 娴佺▼鍒嗙被淇℃伅琛�
+create table WF_CATEGORY
+(
+ ID NUMBER(20) not null
+ constraint PK_WF_CATEGORY
+ primary key,
+ CATEGORY_NAME VARCHAR2(255),
+ CATEGORY_CODE VARCHAR2(255)
+ constraint UNI_CATEGORY_CODE
+ unique,
+ PARENT_ID NUMBER(20),
+ SORT_NUM NUMBER(10),
+ TENANT_ID VARCHAR2(20),
+ CREATE_DEPT NUMBER(20),
+ CREATE_BY NUMBER(20),
+ CREATE_TIME DATE,
+ UPDATE_BY NUMBER(20),
+ UPDATE_TIME DATE
+);
+
+comment on table WF_CATEGORY is '娴佺▼鍒嗙被';
+comment on column WF_CATEGORY.ID is '涓婚敭';
+comment on column WF_CATEGORY.CATEGORY_NAME is '鍒嗙被鍚嶇О';
+comment on column WF_CATEGORY.CATEGORY_CODE is '鍒嗙被缂栫爜';
+comment on column WF_CATEGORY.PARENT_ID is '鐖剁骇id';
+comment on column WF_CATEGORY.SORT_NUM is '鎺掑簭';
+comment on column WF_CATEGORY.TENANT_ID is '绉熸埛缂栧彿';
+comment on column WF_CATEGORY.CREATE_DEPT is '鍒涘缓閮ㄩ棬';
+comment on column WF_CATEGORY.CREATE_BY is '鍒涘缓鑰�';
+comment on column WF_CATEGORY.CREATE_TIME is '鍒涘缓鏃堕棿';
+comment on column WF_CATEGORY.UPDATE_BY is '鏇存柊鑰�';
+comment on column WF_CATEGORY.UPDATE_TIME is '鏇存柊鏃堕棿';
+INSERT INTO wf_category values (1, 'OA', 'OA', 0, 0, '000000', 103, 1, sysdate, 1, sysdate);
+
+create table WF_TASK_BACK_NODE
+(
+ ID NUMBER(20) not null
+ constraint PK_WF_TASK_BACK_NODE
+ primary key,
+ NODE_ID VARCHAR2(255) not null,
+ NODE_NAME VARCHAR2(255) not null,
+ ORDER_NO NUMBER(20) not null,
+ INSTANCE_ID VARCHAR2(255) not null,
+ TASK_TYPE VARCHAR2(255) not null,
+ ASSIGNEE VARCHAR2(2000) not null,
+ TENANT_ID VARCHAR2(20),
+ CREATE_DEPT NUMBER(20),
+ CREATE_BY NUMBER(20),
+ CREATE_TIME DATE,
+ UPDATE_BY NUMBER(20),
+ UPDATE_TIME DATE
+);
+comment on table WF_TASK_BACK_NODE is '鑺傜偣瀹℃壒璁板綍';
+comment on column WF_TASK_BACK_NODE.ID is '涓婚敭';
+comment on column WF_TASK_BACK_NODE.NODE_ID is '鑺傜偣id';
+comment on column WF_TASK_BACK_NODE.NODE_NAME is '鑺傜偣鍚嶇О';
+comment on column WF_TASK_BACK_NODE.ORDER_NO is '鎺掑簭';
+comment on column WF_TASK_BACK_NODE.INSTANCE_ID is '娴佺▼瀹炰緥id';
+comment on column WF_TASK_BACK_NODE.TASK_TYPE is '鑺傜偣绫诲瀷';
+comment on column WF_TASK_BACK_NODE.ASSIGNEE is '瀹℃壒浜�';
+comment on column WF_TASK_BACK_NODE.TENANT_ID is '绉熸埛缂栧彿';
+comment on column WF_TASK_BACK_NODE.CREATE_DEPT is '鍒涘缓閮ㄩ棬';
+comment on column WF_TASK_BACK_NODE.CREATE_BY is '鍒涘缓鑰�';
+comment on column WF_TASK_BACK_NODE.CREATE_TIME is '鍒涘缓鏃堕棿';
+comment on column WF_TASK_BACK_NODE.UPDATE_BY is '鏇存柊鑰�';
+comment on column WF_TASK_BACK_NODE.UPDATE_TIME is '鏇存柊鏃堕棿';
+
+create table WF_DEFINITION_CONFIG
+(
+ ID NUMBER(20) NOT NULL
+ CONSTRAINT PK_WF_DEFINITION_CONFIG
+ PRIMARY KEY,
+ TABLE_NAME VARCHAR2(255) NOT NULL,
+ DEFINITION_ID VARCHAR2(255) NOT NULL,
+ PROCESS_KEY VARCHAR2(255) NOT NULL,
+ VERSION NUMBER(10) NOT NULL,
+ REMARK VARCHAR2(500),
+ TENANT_ID VARCHAR2(20),
+ CREATE_DEPT NUMBER(20),
+ CREATE_BY NUMBER(20),
+ CREATE_TIME DATE,
+ UPDATE_BY NUMBER(20),
+ UPDATE_TIME DATE,
+ constraint uni_definition_id
+ unique (definition_id)
+);
+comment on table WF_DEFINITION_CONFIG is '娴佺▼瀹氫箟閰嶇疆';
+comment on column WF_DEFINITION_CONFIG.ID is '涓婚敭';
+comment on column WF_DEFINITION_CONFIG.TABLE_NAME is '琛ㄥ悕';
+comment on column WF_DEFINITION_CONFIG.DEFINITION_ID is '娴佺▼瀹氫箟ID';
+comment on column WF_DEFINITION_CONFIG.PROCESS_KEY is '娴佺▼KEY';
+comment on column WF_DEFINITION_CONFIG.VERSION is '娴佺▼鐗堟湰';
+comment on column WF_DEFINITION_CONFIG.TENANT_ID is '绉熸埛缂栧彿';
+comment on column WF_DEFINITION_CONFIG.REMARK is '澶囨敞';
+comment on column WF_DEFINITION_CONFIG.CREATE_DEPT is '鍒涘缓閮ㄩ棬';
+comment on column WF_DEFINITION_CONFIG.CREATE_BY is '鍒涘缓鑰�';
+comment on column WF_DEFINITION_CONFIG.CREATE_TIME is '鍒涘缓鏃堕棿';
+comment on column WF_DEFINITION_CONFIG.UPDATE_BY is '鏇存柊鑰�';
+comment on column WF_DEFINITION_CONFIG.UPDATE_TIME is '鏇存柊鏃堕棿';
+
+create table WF_FORM_MANAGE
+(
+ ID NUMBER(20) NOT NULL
+ CONSTRAINT PK_WF_FORM_MANAGE
+ PRIMARY KEY,
+ FORM_NAME VARCHAR2(255) NOT NULL,
+ FORM_TYPE VARCHAR2(255) NOT NULL,
+ ROUTER VARCHAR2(255) NOT NULL,
+ REMARK VARCHAR2(500),
+ TENANT_ID VARCHAR2(20),
+ CREATE_DEPT NUMBER(20),
+ CREATE_BY NUMBER(20),
+ CREATE_TIME DATE,
+ UPDATE_BY NUMBER(20),
+ UPDATE_TIME DATE
+);
+
+comment on table WF_FORM_MANAGE is '琛ㄥ崟绠$悊';
+comment on column WF_FORM_MANAGE.ID is '涓婚敭';
+comment on column WF_FORM_MANAGE.FORM_NAME is '琛ㄥ崟鍚嶇О';
+comment on column WF_FORM_MANAGE.FORM_TYPE is '琛ㄥ崟绫诲瀷';
+comment on column WF_FORM_MANAGE.ROUTER is '璺敱鍦板潃/琛ㄥ崟ID';
+comment on column WF_FORM_MANAGE.REMARK is '澶囨敞';
+comment on column WF_FORM_MANAGE.TENANT_ID is '绉熸埛缂栧彿';
+comment on column WF_FORM_MANAGE.CREATE_DEPT is '鍒涘缓閮ㄩ棬';
+comment on column WF_FORM_MANAGE.CREATE_BY is '鍒涘缓鑰�';
+comment on column WF_FORM_MANAGE.CREATE_TIME is '鍒涘缓鏃堕棿';
+comment on column WF_FORM_MANAGE.UPDATE_BY is '鏇存柊鑰�';
+comment on column WF_FORM_MANAGE.UPDATE_TIME is '鏇存柊鏃堕棿';
+
+insert into wf_form_manage(id, form_name, form_type, router, remark, tenant_id, create_dept, create_by, create_time, update_by, update_time) VALUES (1, '璇峰亣鐢宠', 'static', '/demo/leaveEdit/index', NULL, '000000', 103, 1, sysdate, 1, sysdate);
+
+create table WF_NODE_CONFIG
+(
+ ID NUMBER(20) NOT NULL
+ CONSTRAINT PK_WF_NODE_CONFIG
+ PRIMARY KEY,
+ FORM_ID NUMBER(20),
+ FORM_TYPE VARCHAR2(255),
+ NODE_NAME VARCHAR2(255) NOT NULL,
+ NODE_ID VARCHAR2(255) NOT NULL,
+ DEFINITION_ID VARCHAR2(255) NOT NULL,
+ APPLY_USER_TASK CHAR(1) DEFAULT '0',
+ TENANT_ID VARCHAR2(20),
+ CREATE_DEPT NUMBER(20),
+ CREATE_BY NUMBER(20),
+ CREATE_TIME DATE,
+ UPDATE_BY NUMBER(20),
+ UPDATE_TIME DATE
+);
+
+comment on table WF_NODE_CONFIG is '鑺傜偣閰嶇疆';
+comment on column WF_NODE_CONFIG.ID is '涓婚敭';
+comment on column WF_NODE_CONFIG.FORM_ID is '琛ㄥ崟id';
+comment on column WF_NODE_CONFIG.FORM_TYPE is '琛ㄥ崟绫诲瀷';
+comment on column WF_NODE_CONFIG.NODE_ID is '鑺傜偣id';
+comment on column WF_NODE_CONFIG.NODE_NAME is '鑺傜偣鍚嶇О';
+comment on column WF_NODE_CONFIG.DEFINITION_ID is '娴佺▼瀹氫箟id';
+comment on column WF_NODE_CONFIG.APPLY_USER_TASK is '鏄惁涓虹敵璇蜂汉鑺傜偣 锛�0鏄� 1鍚︼級';
+comment on column WF_NODE_CONFIG.TENANT_ID is '绉熸埛缂栧彿';
+comment on column WF_NODE_CONFIG.CREATE_DEPT is '鍒涘缓閮ㄩ棬';
+comment on column WF_NODE_CONFIG.CREATE_BY is '鍒涘缓鑰�';
+comment on column WF_NODE_CONFIG.CREATE_TIME is '鍒涘缓鏃堕棿';
+comment on column WF_NODE_CONFIG.UPDATE_BY is '鏇存柊鑰�';
+comment on column WF_NODE_CONFIG.UPDATE_TIME is '鏇存柊鏃堕棿';
+
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11638, '璇峰亣鐢宠', 5, 1, 'leave', 'workflow/leave/index', 1, 0, 'C', '0', '0', 'demo:leave:list', '#', 103, 1, sysdate, NULL, NULL, '璇峰亣鐢宠鑿滃崟');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11639, '璇峰亣鐢宠鏌ヨ', 11638, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:query', '#', 103, 1, sysdate, NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11640, '璇峰亣鐢宠鏂板', 11638, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:add', '#', 103, 1, sysdate, NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11641, '璇峰亣鐢宠淇敼', 11638, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:edit', '#', 103, 1, sysdate, NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11642, '璇峰亣鐢宠鍒犻櫎', 11638, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:remove', '#', 103, 1, sysdate, NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11643, '璇峰亣鐢宠瀵煎嚭', 11638, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:export', '#', 103, 1, sysdate, NULL, NULL, '');
+
+INSERT INTO sys_dict_type(dict_id, tenant_id, dict_name, dict_type, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (13, '000000', '涓氬姟鐘舵��', 'wf_business_status', 103, 1, sysdate, NULL, NULL, '涓氬姟鐘舵�佸垪琛�');
+INSERT INTO sys_dict_type(dict_id, tenant_id, dict_name, dict_type, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (14, '000000', '琛ㄥ崟绫诲瀷', 'wf_form_type', 103, 1, sysdate, NULL, NULL, '琛ㄥ崟绫诲瀷鍒楄〃');
+
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (39, '000000', 1, '宸叉挙閿�', 'cancel', 'wf_business_status', '', 'danger', 'N', 103, 1, sysdate, NULL, NULL, '宸叉挙閿�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (40, '000000', 2, '鑽夌', 'draft', 'wf_business_status', '', 'info', 'N', 103, 1, sysdate, NULL, NULL, '鑽夌');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (41, '000000', 3, '寰呭鏍�', 'waiting', 'wf_business_status', '', 'primary', 'N', 103, 1,sysdate, NULL, NULL, '寰呭鏍�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (42, '000000', 4, '宸插畬鎴�', 'finish', 'wf_business_status', '', 'success', 'N', 103, 1, sysdate, NULL, NULL, '宸插畬鎴�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (43, '000000', 5, '宸蹭綔搴�', 'invalid', 'wf_business_status', '', 'danger', 'N', 103, 1, sysdate, NULL, NULL, '宸蹭綔搴�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (44, '000000', 6, '宸查��鍥�', 'back', 'wf_business_status', '', 'danger', 'N', 103, 1, sysdate, NULL, NULL, '宸查��鍥�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (45, '000000', 7, '宸茬粓姝�', 'termination', 'wf_business_status', '', 'danger', 'N', 103, 1,sysdate, NULL, NULL, '宸茬粓姝�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (46, '000000', 1, '鑷畾涔夎〃鍗�', 'static', 'wf_form_type', '', 'success', 'N', 103, 1, sysdate, NULL, NULL, '鑷畾涔夎〃鍗�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (47, '000000', 2, '鍔ㄦ�佽〃鍗�', 'dynamic', 'wf_form_type', '', 'primary', 'N', 103, 1, sysdate, NULL, NULL, '鍔ㄦ�佽〃鍗�');
+
+-- 琛ㄥ崟绠$悊 SQL
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11628, '琛ㄥ崟绠$悊', '11616', '5', 'formManage', 'workflow/formManage/index', 1, 0, 'C', '0', '0', 'workflow:formManage:list', 'tree-table', 103, 1, sysdate, null, null, '琛ㄥ崟绠$悊鑿滃崟');
+
+-- 琛ㄥ崟绠$悊鎸夐挳 SQL
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11644, '琛ㄥ崟绠$悊鏌ヨ', 11628, '1', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:query', '', 103, 1, sysdate, null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11645, '琛ㄥ崟绠$悊鏂板', 11628, '2', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:add', '', 103, 1, sysdate, null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11646, '琛ㄥ崟绠$悊淇敼', 11628, '3', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:edit', '', 103, 1, sysdate, null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11647, '琛ㄥ崟绠$悊鍒犻櫎', 11628, '4', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:remove', '', 103, 1, sysdate, null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11648, '琛ㄥ崟绠$悊瀵煎嚭', 11628, '5', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:export', 'tree-table', 103, 1, sysdate, null, null, '');
diff --git a/script/sql/oracle/oracle_ry_vue_5.X.sql b/script/sql/oracle/oracle_ry_vue_5.X.sql
index ef45c5f..06ea5fe 100644
--- a/script/sql/oracle/oracle_ry_vue_5.X.sql
+++ b/script/sql/oracle/oracle_ry_vue_5.X.sql
@@ -20,7 +20,7 @@
union_id varchar2(255) default null,
scope varchar2(255) default null,
token_type varchar2(255) default null,
- id_token varchar2(255) default null,
+ id_token varchar2(2000) default null,
mac_algorithm varchar2(255) default null,
mac_key varchar2(255) default null,
code varchar2(255) default null,
@@ -165,6 +165,7 @@
parent_id number(20) default 0,
ancestors varchar2(500) default '',
dept_name varchar2(30) default '',
+ dept_category varchar2(100) default null,
order_num number(4) default 0,
leader number(20) default null,
phone varchar2(11) default null,
@@ -186,6 +187,7 @@
comment on column sys_dept.parent_id is '鐖堕儴闂╥d';
comment on column sys_dept.ancestors is '绁栫骇鍒楄〃';
comment on column sys_dept.dept_name is '閮ㄩ棬鍚嶇О';
+comment on column sys_dept.dept_category is '閮ㄩ棬绫诲埆缂栫爜';
comment on column sys_dept.order_num is '鏄剧ず椤哄簭';
comment on column sys_dept.leader is '璐熻矗浜�';
comment on column sys_dept.phone is '鑱旂郴鐢佃瘽';
@@ -201,16 +203,17 @@
-- ----------------------------
-- 鍒濆鍖�-閮ㄩ棬琛ㄦ暟鎹�
-- ----------------------------
-insert into sys_dept values(100, '000000', 0, '0', 'XXX绉戞妧', 0, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-insert into sys_dept values(101, '000000', 100, '0,100', '娣卞湷鎬诲叕鍙�', 1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-insert into sys_dept values(102, '000000', 100, '0,100', '闀挎矙鍒嗗叕鍙�', 2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-insert into sys_dept values(103, '000000', 101, '0,100,101', '鐮斿彂閮ㄩ棬', 1, 1, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-insert into sys_dept values(104, '000000', 101, '0,100,101', '甯傚満閮ㄩ棬', 2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-insert into sys_dept values(105, '000000', 101, '0,100,101', '娴嬭瘯閮ㄩ棬', 3, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-insert into sys_dept values(106, '000000', 101, '0,100,101', '璐㈠姟閮ㄩ棬', 4, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-insert into sys_dept values(107, '000000', 101, '0,100,101', '杩愮淮閮ㄩ棬', 5, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-insert into sys_dept values(108, '000000', 102, '0,100,102', '甯傚満閮ㄩ棬', 1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-insert into sys_dept values(109, '000000', 102, '0,100,102', '璐㈠姟閮ㄩ棬', 2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+
+insert into sys_dept values(100, '000000', 0, '0', 'XXX绉戞妧', null,0, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+insert into sys_dept values(101, '000000', 100, '0,100', '娣卞湷鎬诲叕鍙�', null,1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+insert into sys_dept values(102, '000000', 100, '0,100', '闀挎矙鍒嗗叕鍙�', null,2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+insert into sys_dept values(103, '000000', 101, '0,100,101', '鐮斿彂閮ㄩ棬', null,1, 1, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+insert into sys_dept values(104, '000000', 101, '0,100,101', '甯傚満閮ㄩ棬', null,2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+insert into sys_dept values(105, '000000', 101, '0,100,101', '娴嬭瘯閮ㄩ棬', null,3, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+insert into sys_dept values(106, '000000', 101, '0,100,101', '璐㈠姟閮ㄩ棬', null,4, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+insert into sys_dept values(107, '000000', 101, '0,100,101', '杩愮淮閮ㄩ棬', null,5, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+insert into sys_dept values(108, '000000', 102, '0,100,102', '甯傚満閮ㄩ棬', null,1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
+insert into sys_dept values(109, '000000', 102, '0,100,102', '璐㈠姟閮ㄩ棬', null,2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate, null, null);
-- ----------------------------
@@ -269,8 +272,8 @@
-- 鍒濆鍖�-鐢ㄦ埛淇℃伅琛ㄦ暟鎹�
-- ----------------------------
insert into sys_user values(1, '000000', 103, 'admin', '鐤媯鐨勭嫯瀛怢i', 'sys_user', 'crazyLionLi@163.com', '15888888888', '1', null, '$2a$10$7JB720yubVSZvUI0rEqK/.VqGOZTH.ulu33dHOiBE8ByOhJIrdAu2', '0', '0', '127.0.0.1', sysdate, 103, 1, sysdate, null, null, '绠$悊鍛�');
-insert into sys_user values(2, '000000', 105, 'lionli', '鐤媯鐨勭嫯瀛怢i', 'sys_user', 'crazyLionLi@qq.com', '15666666666', '1', null, '$2a$10$7JB720yubVSZvUI0rEqK/.VqGOZTH.ulu33dHOiBE8ByOhJIrdAu2', '0', '0', '127.0.0.1', sysdate, 103, 1, sysdate, null, null, '娴嬭瘯鍛�');
-
+insert into sys_user values(3, '000000', 108, 'test', '鏈儴闂ㄥ強浠ヤ笅 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', sysdate, 103, 1, sysdate, null, null, '');
+insert into sys_user values(4, '000000', 102, 'test1', '浠呮湰浜� 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', sysdate, 103, 1, sysdate, null, null, '');
-- ----------------------------
-- 3銆佸矖浣嶄俊鎭〃
@@ -278,7 +281,9 @@
create table sys_post (
post_id number(20) not null,
tenant_id varchar2(20) default '000000',
+ dept_id number(20) not null,
post_code varchar2(64) not null,
+ post_category varchar2(64) default null,
post_name varchar2(50) not null,
post_sort number(4) not null,
status char(1) not null,
@@ -295,7 +300,9 @@
comment on table sys_post is '宀椾綅淇℃伅琛�';
comment on column sys_post.post_id is '宀椾綅ID';
comment on column sys_post.tenant_id is '绉熸埛缂栧彿';
+comment on column sys_post.dept_id is '閮ㄩ棬id';
comment on column sys_post.post_code is '宀椾綅缂栫爜';
+comment on column sys_post.post_category is '宀椾綅绫诲埆缂栫爜';
comment on column sys_post.post_name is '宀椾綅鍚嶇О';
comment on column sys_post.post_sort is '鏄剧ず椤哄簭';
comment on column sys_post.status is '鐘舵�侊紙0姝e父 1鍋滅敤锛�';
@@ -309,10 +316,10 @@
-- ----------------------------
-- 鍒濆鍖�-宀椾綅淇℃伅琛ㄦ暟鎹�
-- ----------------------------
-insert into sys_post values(1, '000000', 'ceo', '钁d簨闀�', 1, '0', 103, 1, sysdate, null, null, '');
-insert into sys_post values(2, '000000', 'se', '椤圭洰缁忕悊', 2, '0', 103, 1, sysdate, null, null, '');
-insert into sys_post values(3, '000000', 'hr', '浜哄姏璧勬簮', 3, '0', 103, 1, sysdate, null, null, '');
-insert into sys_post values(4, '000000', 'user', '鏅�氬憳宸�', 4, '0', 103, 1, sysdate, null, null, '');
+insert into sys_post values(1, '000000', 103, 'ceo', null, '钁d簨闀�', 1, '0', 103, 1, sysdate, null, null, '');
+insert into sys_post values(2, '000000', 100, 'se', null, '椤圭洰缁忕悊', 2, '0', 103, 1, sysdate, null, null, '');
+insert into sys_post values(3, '000000', 100, 'hr', null, '浜哄姏璧勬簮', 3, '0', 103, 1, sysdate, null, null, '');
+insert into sys_post values(4, '000000', 100, 'user', null, '鏅�氬憳宸�', 4, '0', 103, 1, sysdate, null, null, '');
-- ----------------------------
@@ -361,8 +368,8 @@
-- 鍒濆鍖�-瑙掕壊淇℃伅琛ㄦ暟鎹�
-- ----------------------------
insert into sys_role values('1', '000000', '瓒呯骇绠$悊鍛�', 'superadmin', 1, 1, 1, 1, '0', '0', 103, 1, sysdate, null, null, '瓒呯骇绠$悊鍛�');
-insert into sys_role values('2', '000000', '鏅�氳鑹�', 'common', 2, 2, 1, 1, '0', '0', 103, 1, sysdate, null, null, '鏅�氳鑹�');
-
+insert into sys_role values('3', '000000', '鏈儴闂ㄥ強浠ヤ笅', 'test1', 3, 4, 1, 1, '0', '0', 103, 1, sysdate, null, null, null);
+insert into sys_role values('4', '000000', '浠呮湰浜�', 'test2', 4, 5, 1, 1, '0', '0', 103, 1, sysdate, null, null, null);
-- ----------------------------
-- 5銆佽彍鍗曟潈闄愯〃
@@ -423,6 +430,7 @@
insert into sys_menu values('2', '绯荤粺鐩戞帶', '0', '3', 'monitor', null, '', 1, 0, 'M', '0', '0', '', 'monitor', 103, 1, sysdate, null, null, '绯荤粺鐩戞帶鐩綍');
insert into sys_menu values('3', '绯荤粺宸ュ叿', '0', '4', 'tool', null, '', 1, 0, 'M', '0', '0', '', 'tool', 103, 1, sysdate, null, null, '绯荤粺宸ュ叿鐩綍');
insert into sys_menu values('4', 'PLUS瀹樼綉', '0', '5', 'https://gitee.com/dromara/RuoYi-Vue-Plus', null, '', 0, 0, 'M', '0', '0', '', 'guide', 103, 1, sysdate, null, null, 'RuoYi-Vue-Plus瀹樼綉鍦板潃');
+insert into sys_menu values('5', '娴嬭瘯鑿滃崟', '0', '5', 'demo', null, '', 1, 0, 'M', '0', '0', null, 'star', 103, 1, sysdate, null, null, '');
-- 浜岀骇鑿滃崟
insert into sys_menu values('100', '鐢ㄦ埛绠$悊', '1', '1', 'user', 'system/user/index', '', 1, 0, 'C', '0', '0', 'system:user:list', 'user', 103, 1, sysdate, null, null, '鐢ㄦ埛绠$悊鑿滃崟');
insert into sys_menu values('101', '瑙掕壊绠$悊', '1', '2', 'role', 'system/role/index', '', 1, 0, 'C', '0', '0', 'system:role:list', 'peoples', 103, 1, sysdate, null, null, '瑙掕壊绠$悊鑿滃崟');
@@ -444,8 +452,8 @@
insert into sys_menu values('117', 'Admin鐩戞帶', '2', '5', 'Admin', 'monitor/admin/index', '', 1, 0, 'C', '0', '0', 'monitor:admin:list', 'dashboard', 103, 1, sysdate, null, null, 'Admin鐩戞帶鑿滃崟');
-- oss鑿滃崟
insert into sys_menu values('118', '鏂囦欢绠$悊', '1', '10', 'oss', 'system/oss/index', '', 1, 0, 'C', '0', '0', 'system:oss:list', 'upload', 103, 1, sysdate, null, null, '鏂囦欢绠$悊鑿滃崟');
--- powerjob server鎺у埗鍙�
-insert into sys_menu values('120', '浠诲姟璋冨害涓績', '2', '5', 'powerjob', 'monitor/powerjob/index', '', 1, 0, 'C', '0', '0', 'monitor:powerjob:list', 'job', 103, 1, sysdate, null, null, 'PowerJob鎺у埗鍙拌彍鍗�');
+-- snail-job server鎺у埗鍙�
+insert into sys_menu values('120', '浠诲姟璋冨害涓績', '2', '5', 'snailjob', 'monitor/snailjob/index', '', 1, 0, 'C', '0', '0', 'monitor:snailjob:list', 'job', 103, 1, sysdate, null, null, 'snailjob鎺у埗鍙拌彍鍗�');
-- 涓夌骇鑿滃崟
insert into sys_menu values('500', '鎿嶄綔鏃ュ織', '108', '1', 'operlog', 'monitor/operlog/index', '', 1, 0, 'C', '0', '0', 'monitor:operlog:list', 'form', 103, 1, sysdate, null, null, '鎿嶄綔鏃ュ織鑿滃崟');
@@ -544,6 +552,20 @@
insert into sys_menu values('1063', '瀹㈡埛绔鐞嗕慨鏀�', '123', '3', '#', '', '', 1, 0, 'F', '0', '0', 'system:client:edit', '#', 103, 1, sysdate, null, null, '');
insert into sys_menu values('1064', '瀹㈡埛绔鐞嗗垹闄�', '123', '4', '#', '', '', 1, 0, 'F', '0', '0', 'system:client:remove', '#', 103, 1, sysdate, null, null, '');
insert into sys_menu values('1065', '瀹㈡埛绔鐞嗗鍑�', '123', '5', '#', '', '', 1, 0, 'F', '0', '0', 'system:client:export', '#', 103, 1, sysdate, null, null, '');
+-- 娴嬭瘯鑿滃崟
+insert into sys_menu values('1500', '娴嬭瘯鍗曡〃', '5', '1', 'demo', 'demo/demo/index', '', 1, 0, 'C', '0', '0', 'demo:demo:list', '#', 103, 1, sysdate, null, null, '娴嬭瘯鍗曡〃鑿滃崟');
+insert into sys_menu values('1501', '娴嬭瘯鍗曡〃鏌ヨ', '1500', '1', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:query', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values('1502', '娴嬭瘯鍗曡〃鏂板', '1500', '2', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:add', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values('1503', '娴嬭瘯鍗曡〃淇敼', '1500', '3', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:edit', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values('1504', '娴嬭瘯鍗曡〃鍒犻櫎', '1500', '4', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:remove', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values('1505', '娴嬭瘯鍗曡〃瀵煎嚭', '1500', '5', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:export', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values('1506', '娴嬭瘯鏍戣〃', '5', '1', 'tree', 'demo/tree/index', '', 1, 0, 'C', '0', '0', 'demo:tree:list', '#', 103, 1, sysdate, null, null, '娴嬭瘯鏍戣〃鑿滃崟');
+insert into sys_menu values('1507', '娴嬭瘯鏍戣〃鏌ヨ', '1506', '1', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:query', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values('1508', '娴嬭瘯鏍戣〃鏂板', '1506', '2', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:add', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values('1509', '娴嬭瘯鏍戣〃淇敼', '1506', '3', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:edit', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values('1510', '娴嬭瘯鏍戣〃鍒犻櫎', '1506', '4', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:remove', '#', 103, 1, sysdate, null, null, '');
+insert into sys_menu values('1511', '娴嬭瘯鏍戣〃瀵煎嚭', '1506', '5', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:export', '#', 103, 1, sysdate, null, null, '');
+
-- ----------------------------
-- 6銆佺敤鎴峰拰瑙掕壊鍏宠仈琛� 鐢ㄦ埛N-1瑙掕壊
@@ -563,8 +585,8 @@
-- 鍒濆鍖�-鐢ㄦ埛鍜岃鑹插叧鑱旇〃鏁版嵁
-- ----------------------------
insert into sys_user_role values ('1', '1');
-insert into sys_user_role values ('2', '2');
-
+insert into sys_user_role values ('3', '3');
+insert into sys_user_role values ('4', '4');
-- ----------------------------
-- 7銆佽鑹插拰鑿滃崟鍏宠仈琛� 瑙掕壊1-N鑿滃崟
@@ -583,90 +605,89 @@
-- ----------------------------
-- 鍒濆鍖�-瑙掕壊鍜岃彍鍗曞叧鑱旇〃鏁版嵁
-- ----------------------------
-insert into sys_role_menu values ('2', '1');
-insert into sys_role_menu values ('2', '2');
-insert into sys_role_menu values ('2', '3');
-insert into sys_role_menu values ('2', '4');
-insert into sys_role_menu values ('2', '100');
-insert into sys_role_menu values ('2', '101');
-insert into sys_role_menu values ('2', '102');
-insert into sys_role_menu values ('2', '103');
-insert into sys_role_menu values ('2', '104');
-insert into sys_role_menu values ('2', '105');
-insert into sys_role_menu values ('2', '106');
-insert into sys_role_menu values ('2', '107');
-insert into sys_role_menu values ('2', '108');
-insert into sys_role_menu values ('2', '109');
-insert into sys_role_menu values ('2', '110');
-insert into sys_role_menu values ('2', '111');
-insert into sys_role_menu values ('2', '112');
-insert into sys_role_menu values ('2', '113');
-insert into sys_role_menu values ('2', '114');
-insert into sys_role_menu values ('2', '115');
-insert into sys_role_menu values ('2', '116');
-insert into sys_role_menu values ('2', '500');
-insert into sys_role_menu values ('2', '501');
-insert into sys_role_menu values ('2', '1000');
-insert into sys_role_menu values ('2', '1001');
-insert into sys_role_menu values ('2', '1002');
-insert into sys_role_menu values ('2', '1003');
-insert into sys_role_menu values ('2', '1004');
-insert into sys_role_menu values ('2', '1005');
-insert into sys_role_menu values ('2', '1006');
-insert into sys_role_menu values ('2', '1007');
-insert into sys_role_menu values ('2', '1008');
-insert into sys_role_menu values ('2', '1009');
-insert into sys_role_menu values ('2', '1010');
-insert into sys_role_menu values ('2', '1011');
-insert into sys_role_menu values ('2', '1012');
-insert into sys_role_menu values ('2', '1013');
-insert into sys_role_menu values ('2', '1014');
-insert into sys_role_menu values ('2', '1015');
-insert into sys_role_menu values ('2', '1016');
-insert into sys_role_menu values ('2', '1017');
-insert into sys_role_menu values ('2', '1018');
-insert into sys_role_menu values ('2', '1019');
-insert into sys_role_menu values ('2', '1020');
-insert into sys_role_menu values ('2', '1021');
-insert into sys_role_menu values ('2', '1022');
-insert into sys_role_menu values ('2', '1023');
-insert into sys_role_menu values ('2', '1024');
-insert into sys_role_menu values ('2', '1025');
-insert into sys_role_menu values ('2', '1026');
-insert into sys_role_menu values ('2', '1027');
-insert into sys_role_menu values ('2', '1028');
-insert into sys_role_menu values ('2', '1029');
-insert into sys_role_menu values ('2', '1030');
-insert into sys_role_menu values ('2', '1031');
-insert into sys_role_menu values ('2', '1032');
-insert into sys_role_menu values ('2', '1033');
-insert into sys_role_menu values ('2', '1034');
-insert into sys_role_menu values ('2', '1035');
-insert into sys_role_menu values ('2', '1036');
-insert into sys_role_menu values ('2', '1037');
-insert into sys_role_menu values ('2', '1038');
-insert into sys_role_menu values ('2', '1039');
-insert into sys_role_menu values ('2', '1040');
-insert into sys_role_menu values ('2', '1041');
-insert into sys_role_menu values ('2', '1042');
-insert into sys_role_menu values ('2', '1043');
-insert into sys_role_menu values ('2', '1044');
-insert into sys_role_menu values ('2', '1045');
-insert into sys_role_menu values ('2', '1050');
-insert into sys_role_menu values ('2', '1046');
-insert into sys_role_menu values ('2', '1047');
-insert into sys_role_menu values ('2', '1048');
-insert into sys_role_menu values ('2', '1055');
-insert into sys_role_menu values ('2', '1056');
-insert into sys_role_menu values ('2', '1057');
-insert into sys_role_menu values ('2', '1058');
-insert into sys_role_menu values ('2', '1059');
-insert into sys_role_menu values ('2', '1060');
-insert into sys_role_menu values ('2', '1061');
-insert into sys_role_menu values ('2', '1062');
-insert into sys_role_menu values ('2', '1063');
-insert into sys_role_menu values ('2', '1064');
-insert into sys_role_menu values ('2', '1065');
+insert into sys_role_menu values ('3', '1');
+insert into sys_role_menu values ('3', '5');
+insert into sys_role_menu values ('3', '100');
+insert into sys_role_menu values ('3', '101');
+insert into sys_role_menu values ('3', '102');
+insert into sys_role_menu values ('3', '103');
+insert into sys_role_menu values ('3', '104');
+insert into sys_role_menu values ('3', '105');
+insert into sys_role_menu values ('3', '106');
+insert into sys_role_menu values ('3', '107');
+insert into sys_role_menu values ('3', '108');
+insert into sys_role_menu values ('3', '500');
+insert into sys_role_menu values ('3', '501');
+insert into sys_role_menu values ('3', '1001');
+insert into sys_role_menu values ('3', '1002');
+insert into sys_role_menu values ('3', '1003');
+insert into sys_role_menu values ('3', '1004');
+insert into sys_role_menu values ('3', '1005');
+insert into sys_role_menu values ('3', '1006');
+insert into sys_role_menu values ('3', '1007');
+insert into sys_role_menu values ('3', '1008');
+insert into sys_role_menu values ('3', '1009');
+insert into sys_role_menu values ('3', '1010');
+insert into sys_role_menu values ('3', '1011');
+insert into sys_role_menu values ('3', '1012');
+insert into sys_role_menu values ('3', '1013');
+insert into sys_role_menu values ('3', '1014');
+insert into sys_role_menu values ('3', '1015');
+insert into sys_role_menu values ('3', '1016');
+insert into sys_role_menu values ('3', '1017');
+insert into sys_role_menu values ('3', '1018');
+insert into sys_role_menu values ('3', '1019');
+insert into sys_role_menu values ('3', '1020');
+insert into sys_role_menu values ('3', '1021');
+insert into sys_role_menu values ('3', '1022');
+insert into sys_role_menu values ('3', '1023');
+insert into sys_role_menu values ('3', '1024');
+insert into sys_role_menu values ('3', '1025');
+insert into sys_role_menu values ('3', '1026');
+insert into sys_role_menu values ('3', '1027');
+insert into sys_role_menu values ('3', '1028');
+insert into sys_role_menu values ('3', '1029');
+insert into sys_role_menu values ('3', '1030');
+insert into sys_role_menu values ('3', '1031');
+insert into sys_role_menu values ('3', '1032');
+insert into sys_role_menu values ('3', '1033');
+insert into sys_role_menu values ('3', '1034');
+insert into sys_role_menu values ('3', '1035');
+insert into sys_role_menu values ('3', '1036');
+insert into sys_role_menu values ('3', '1037');
+insert into sys_role_menu values ('3', '1038');
+insert into sys_role_menu values ('3', '1039');
+insert into sys_role_menu values ('3', '1040');
+insert into sys_role_menu values ('3', '1041');
+insert into sys_role_menu values ('3', '1042');
+insert into sys_role_menu values ('3', '1043');
+insert into sys_role_menu values ('3', '1044');
+insert into sys_role_menu values ('3', '1045');
+insert into sys_role_menu values ('3', '1500');
+insert into sys_role_menu values ('3', '1501');
+insert into sys_role_menu values ('3', '1502');
+insert into sys_role_menu values ('3', '1503');
+insert into sys_role_menu values ('3', '1504');
+insert into sys_role_menu values ('3', '1505');
+insert into sys_role_menu values ('3', '1506');
+insert into sys_role_menu values ('3', '1507');
+insert into sys_role_menu values ('3', '1508');
+insert into sys_role_menu values ('3', '1509');
+insert into sys_role_menu values ('3', '1510');
+insert into sys_role_menu values ('3', '1511');
+insert into sys_role_menu values ('4', '5');
+insert into sys_role_menu values ('4', '1500');
+insert into sys_role_menu values ('4', '1501');
+insert into sys_role_menu values ('4', '1502');
+insert into sys_role_menu values ('4', '1503');
+insert into sys_role_menu values ('4', '1504');
+insert into sys_role_menu values ('4', '1505');
+insert into sys_role_menu values ('4', '1506');
+insert into sys_role_menu values ('4', '1507');
+insert into sys_role_menu values ('4', '1508');
+insert into sys_role_menu values ('4', '1509');
+insert into sys_role_menu values ('4', '1510');
+insert into sys_role_menu values ('4', '1511');
-- ----------------------------
-- 8銆佽鑹插拰閮ㄩ棬鍏宠仈琛� 瑙掕壊1-N閮ㄩ棬
@@ -681,13 +702,6 @@
comment on table sys_role_dept is '瑙掕壊鍜岄儴闂ㄥ叧鑱旇〃';
comment on column sys_role_dept.role_id is '瑙掕壊ID';
comment on column sys_role_dept.dept_id is '閮ㄩ棬ID';
-
--- ----------------------------
--- 鍒濆鍖�-瑙掕壊鍜岄儴闂ㄥ叧鑱旇〃鏁版嵁
--- ----------------------------
-insert into sys_role_dept values ('2', '100');
-insert into sys_role_dept values ('2', '101');
-insert into sys_role_dept values ('2', '105');
-- ----------------------------
@@ -708,8 +722,6 @@
-- 鍒濆鍖�-鐢ㄦ埛涓庡矖浣嶅叧鑱旇〃鏁版嵁
-- ----------------------------
insert into sys_user_post values ('1', '1');
-insert into sys_user_post values ('2', '2');
-
-- ----------------------------
-- 10銆佹搷浣滄棩蹇楄褰�
@@ -1174,7 +1186,7 @@
alter table sys_oss_config add constraint pk_sys_oss_config primary key (oss_config_id);
comment on table sys_oss_config is '瀵硅薄瀛樺偍閰嶇疆琛�';
-comment on column sys_oss_config.oss_config_id is '涓诲缓';
+comment on column sys_oss_config.oss_config_id is '涓婚敭';
comment on column sys_oss_config.tenant_id is '绉熸埛缂栫爜';
comment on column sys_oss_config.config_key is '閰嶇疆key';
comment on column sys_oss_config.access_key is 'accesskey';
@@ -1225,7 +1237,7 @@
alter table sys_client add constraint pk_sys_client primary key (id);
comment on table sys_client is '绯荤粺鎺堟潈琛�';
-comment on column sys_client.id is '涓诲缓';
+comment on column sys_client.id is '涓婚敭';
comment on column sys_client.client_id is '瀹㈡埛绔痠d';
comment on column sys_client.client_key is '瀹㈡埛绔痥ey';
comment on column sys_client.client_secret is '瀹㈡埛绔閽�';
@@ -1244,6 +1256,102 @@
insert into sys_client values (1, 'e5cd7e4891bf95d1d19206ce24a7b32e', 'pc', 'pc123', 'password,social', 'pc', 1800, 604800, 0, 0, 103, 1, sysdate, 1, sysdate);
insert into sys_client values (2, '428a8310cd442757ae699df5d894f051', 'app', 'app123', 'password,sms,social', 'android', 1800, 604800, 0, 0, 103, 1, sysdate, 1, sysdate);
+create table test_demo (
+ id number(20) not null,
+ tenant_id varchar2(20) default '000000',
+ dept_id number(20) default null,
+ user_id number(20) default null,
+ order_num number(10) default 0,
+ test_key varchar2(255) default null,
+ value varchar2(255) default null,
+ version number(10) default 0,
+ create_dept number(20) default null,
+ create_time date,
+ create_by number(20) default null,
+ update_time date,
+ update_by number(20) default null,
+ del_flag number(2) default 0
+);
+
+alter table test_demo add constraint pk_test_demo primary key (id);
+
+comment on table test_demo is '娴嬭瘯鍗曡〃';
+comment on column test_demo.id is '涓婚敭';
+comment on column test_demo.tenant_id is '绉熸埛缂栧彿';
+comment on column test_demo.dept_id is '閮ㄩ棬id';
+comment on column test_demo.user_id is '鐢ㄦ埛id';
+comment on column test_demo.order_num is '鎺掑簭鍙�';
+comment on column test_demo.test_key is 'key閿�';
+comment on column test_demo.value is '鍊�';
+comment on column test_demo.version is '鐗堟湰';
+comment on column test_demo.create_dept is '鍒涘缓閮ㄩ棬';
+comment on column test_demo.create_time is '鍒涘缓鏃堕棿';
+comment on column test_demo.create_by is '鍒涘缓浜�';
+comment on column test_demo.update_time is '鏇存柊鏃堕棿';
+comment on column test_demo.update_by is '鏇存柊浜�';
+comment on column test_demo.del_flag is '鍒犻櫎鏍囧織';
+
+create table test_tree (
+ id number(20) not null,
+ tenant_id varchar2(20) default '000000',
+ parent_id number(20) default 0,
+ dept_id number(20) default null,
+ user_id number(20) default null,
+ tree_name varchar2(255) default null,
+ version number(10) default 0,
+ create_dept number(20) default null,
+ create_time date,
+ create_by number(20) default null,
+ update_time date,
+ update_by number(20) default null,
+ del_flag number(2) default 0
+);
+
+alter table test_tree add constraint pk_test_tree primary key (id);
+
+comment on table test_tree is '娴嬭瘯鏍戣〃';
+comment on column test_tree.id is '涓婚敭';
+comment on column test_tree.tenant_id is '绉熸埛缂栧彿';
+comment on column test_tree.parent_id is '鐖秈d';
+comment on column test_tree.dept_id is '閮ㄩ棬id';
+comment on column test_tree.user_id is '鐢ㄦ埛id';
+comment on column test_tree.tree_name is '鍊�';
+comment on column test_tree.version is '鐗堟湰';
+comment on column test_tree.create_dept is '鍒涘缓閮ㄩ棬';
+comment on column test_tree.create_time is '鍒涘缓鏃堕棿';
+comment on column test_tree.create_by is '鍒涘缓浜�';
+comment on column test_tree.update_time is '鏇存柊鏃堕棿';
+comment on column test_tree.update_by is '鏇存柊浜�';
+comment on column test_tree.del_flag is '鍒犻櫎鏍囧織';
+
+insert into test_demo values (1, '000000', 102, 4, 1, '娴嬭瘯鏁版嵁鏉冮檺', '娴嬭瘯', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (2, '000000', 102, 3, 2, '瀛愯妭鐐�1', '111', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (3, '000000', 102, 3, 3, '瀛愯妭鐐�2', '222', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (4, '000000', 108, 4, 4, '娴嬭瘯鏁版嵁', 'demo', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (5, '000000', 108, 3, 13, '瀛愯妭鐐�11', '1111', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (6, '000000', 108, 3, 12, '瀛愯妭鐐�22', '2222', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (7, '000000', 108, 3, 11, '瀛愯妭鐐�33', '3333', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (8, '000000', 108, 3, 10, '瀛愯妭鐐�44', '4444', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (9, '000000', 108, 3, 9, '瀛愯妭鐐�55', '5555', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (10, '000000', 108, 3, 8, '瀛愯妭鐐�66', '6666', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (11, '000000', 108, 3, 7, '瀛愯妭鐐�77', '7777', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (12, '000000', 108, 3, 6, '瀛愯妭鐐�88', '8888', 0, 103, sysdate, 1, null, null, 0);
+insert into test_demo values (13, '000000', 108, 3, 5, '瀛愯妭鐐�99', '9999', 0, 103, sysdate, 1, null, null, 0);
+
+insert into test_tree values (1, '000000', 0, 102, 4, '娴嬭瘯鏁版嵁鏉冮檺', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (2, '000000', 1, 102, 3, '瀛愯妭鐐�1', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (3, '000000', 2, 102, 3, '瀛愯妭鐐�2', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (4, '000000', 0, 108, 4, '娴嬭瘯鏍�1', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (5, '000000', 4, 108, 3, '瀛愯妭鐐�11', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (6, '000000', 4, 108, 3, '瀛愯妭鐐�22', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (7, '000000', 4, 108, 3, '瀛愯妭鐐�33', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (8, '000000', 5, 108, 3, '瀛愯妭鐐�44', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (9, '000000', 6, 108, 3, '瀛愯妭鐐�55', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (10, '000000', 7, 108, 3, '瀛愯妭鐐�66', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (11, '000000', 7, 108, 3, '瀛愯妭鐐�77', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (12, '000000', 10, 108, 3, '瀛愯妭鐐�88', 0, 103, sysdate, 1, null, null, 0);
+insert into test_tree values (13, '000000', 10, 108, 3, '瀛愯妭鐐�99', 0, 103, sysdate, 1, null, null, 0);
+
-- ----------------------------
-- 閽╁瓙 锛岀敤浜巗ession杩炴帴涔嬪悗 鑷姩璁剧疆榛樿鐨刣ate绫诲瀷鏍煎紡鍖� 绠�鍖栨椂闂存煡璇�
diff --git a/script/sql/oracle/oracle_test.sql b/script/sql/oracle/oracle_test.sql
deleted file mode 100644
index fd93786..0000000
--- a/script/sql/oracle/oracle_test.sql
+++ /dev/null
@@ -1,204 +0,0 @@
-create table test_demo (
- id number(20) not null,
- tenant_id varchar2(20) default '000000',
- dept_id number(20) default null,
- user_id number(20) default null,
- order_num number(10) default 0,
- test_key varchar2(255) default null,
- value varchar2(255) default null,
- version number(10) default 0,
- create_dept number(20) default null,
- create_time date,
- create_by number(20) default null,
- update_time date,
- update_by number(20) default null,
- del_flag number(2) default 0
-);
-
-alter table test_demo add constraint pk_test_demo primary key (id);
-
-comment on table test_demo is '娴嬭瘯鍗曡〃';
-comment on column test_demo.id is '涓婚敭';
-comment on column test_demo.tenant_id is '绉熸埛缂栧彿';
-comment on column test_demo.dept_id is '閮ㄩ棬id';
-comment on column test_demo.user_id is '鐢ㄦ埛id';
-comment on column test_demo.order_num is '鎺掑簭鍙�';
-comment on column test_demo.test_key is 'key閿�';
-comment on column test_demo.value is '鍊�';
-comment on column test_demo.version is '鐗堟湰';
-comment on column test_demo.create_dept is '鍒涘缓閮ㄩ棬';
-comment on column test_demo.create_time is '鍒涘缓鏃堕棿';
-comment on column test_demo.create_by is '鍒涘缓浜�';
-comment on column test_demo.update_time is '鏇存柊鏃堕棿';
-comment on column test_demo.update_by is '鏇存柊浜�';
-comment on column test_demo.del_flag is '鍒犻櫎鏍囧織';
-
-create table test_tree (
- id number(20) not null,
- tenant_id varchar2(20) default '000000',
- parent_id number(20) default 0,
- dept_id number(20) default null,
- user_id number(20) default null,
- tree_name varchar2(255) default null,
- version number(10) default 0,
- create_dept number(20) default null,
- create_time date,
- create_by number(20) default null,
- update_time date,
- update_by number(20) default null,
- del_flag number(2) default 0
-);
-
-alter table test_tree add constraint pk_test_tree primary key (id);
-
-comment on table test_tree is '娴嬭瘯鏍戣〃';
-comment on column test_tree.id is '涓婚敭';
-comment on column test_tree.tenant_id is '绉熸埛缂栧彿';
-comment on column test_tree.parent_id is '鐖秈d';
-comment on column test_tree.dept_id is '閮ㄩ棬id';
-comment on column test_tree.user_id is '鐢ㄦ埛id';
-comment on column test_tree.tree_name is '鍊�';
-comment on column test_tree.version is '鐗堟湰';
-comment on column test_tree.create_dept is '鍒涘缓閮ㄩ棬';
-comment on column test_tree.create_time is '鍒涘缓鏃堕棿';
-comment on column test_tree.create_by is '鍒涘缓浜�';
-comment on column test_tree.update_time is '鏇存柊鏃堕棿';
-comment on column test_tree.update_by is '鏇存柊浜�';
-comment on column test_tree.del_flag is '鍒犻櫎鏍囧織';
-
-insert into sys_user(user_id, tenant_id, dept_id, user_name, nick_name, user_type, email, phonenumber, sex, avatar, password, status, del_flag, login_ip, login_date, create_dept, create_by, create_time, update_by, update_time, remark) values (3, '000000', 108, 'test', '鏈儴闂ㄥ強浠ヤ笅 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', sysdate, 103, 1, sysdate, 3, sysdate, null);
-insert into sys_user(user_id, tenant_id, dept_id, user_name, nick_name, user_type, email, phonenumber, sex, avatar, password, status, del_flag, login_ip, login_date, create_dept, create_by, create_time, update_by, update_time, remark) values (4, '000000', 102, 'test1', '浠呮湰浜� 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', sysdate, 103, 1, sysdate, 4, sysdate, null);
-
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (5, '娴嬭瘯鑿滃崟', 0, 5, 'demo', null, 1, 0, 'M', '0', '0', null, 'star', 103, 1, sysdate, 1, sysdate, '');
-
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1500, '娴嬭瘯鍗曡〃', 5, 1, 'demo', 'demo/demo/index', 1, 0, 'C', '0', '0', 'demo:demo:list', '#', 103, 1, sysdate, null, null, '娴嬭瘯鍗曡〃鑿滃崟');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1501, '娴嬭瘯鍗曡〃鏌ヨ', 1500, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:query', '#', 103, 1, sysdate, null, null, '');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1502, '娴嬭瘯鍗曡〃鏂板', 1500, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:add', '#', 103, 1, sysdate, null, null, '');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1503, '娴嬭瘯鍗曡〃淇敼', 1500, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:edit', '#', 103, 1, sysdate, null, null, '');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1504, '娴嬭瘯鍗曡〃鍒犻櫎', 1500, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:remove', '#', 103, 1, sysdate, null, null, '');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1505, '娴嬭瘯鍗曡〃瀵煎嚭', 1500, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:export', '#', 103, 1, sysdate, null, null, '');
-
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1506, '娴嬭瘯鏍戣〃', 5, 1, 'tree', 'demo/tree/index', 1, 0, 'C', '0', '0', 'demo:tree:list', '#', 103, 1, sysdate, null, null, '娴嬭瘯鏍戣〃鑿滃崟');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1507, '娴嬭瘯鏍戣〃鏌ヨ', 1506, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:query', '#', 103, 1, sysdate, null, null, '');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1508, '娴嬭瘯鏍戣〃鏂板', 1506, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:add', '#', 103, 1, sysdate, null, null, '');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1509, '娴嬭瘯鏍戣〃淇敼', 1506, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:edit', '#', 103, 1, sysdate, null, null, '');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1510, '娴嬭瘯鏍戣〃鍒犻櫎', 1506, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:remove', '#', 103, 1, sysdate, null, null, '');
-insert into sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) values (1511, '娴嬭瘯鏍戣〃瀵煎嚭', 1506, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:export', '#', 103, 1, sysdate, null, null, '');
-
-insert into sys_role(role_id, tenant_id, role_name, role_key, role_sort, data_scope, menu_check_strictly, dept_check_strictly, status, del_flag, create_dept, create_by, create_time, update_by, update_time, remark) values (3, '000000', '鏈儴闂ㄥ強浠ヤ笅', 'test1', 3, '4', 1, 1, '0', '0', 103, 1, sysdate, null, null, null);
-insert into sys_role(role_id, tenant_id, role_name, role_key, role_sort, data_scope, menu_check_strictly, dept_check_strictly, status, del_flag, create_dept, create_by, create_time, update_by, update_time, remark) values (4, '000000', '浠呮湰浜�', 'test2', 4, '5', 1, 1, '0', '0', 103, 1, sysdate, null, null, null);
-
-insert into sys_role_menu(role_id, menu_id) values (3, 1);
-insert into sys_role_menu(role_id, menu_id) values (3, 5);
-insert into sys_role_menu(role_id, menu_id) values (3, 100);
-insert into sys_role_menu(role_id, menu_id) values (3, 101);
-insert into sys_role_menu(role_id, menu_id) values (3, 102);
-insert into sys_role_menu(role_id, menu_id) values (3, 103);
-insert into sys_role_menu(role_id, menu_id) values (3, 104);
-insert into sys_role_menu(role_id, menu_id) values (3, 105);
-insert into sys_role_menu(role_id, menu_id) values (3, 106);
-insert into sys_role_menu(role_id, menu_id) values (3, 107);
-insert into sys_role_menu(role_id, menu_id) values (3, 108);
-insert into sys_role_menu(role_id, menu_id) values (3, 500);
-insert into sys_role_menu(role_id, menu_id) values (3, 501);
-insert into sys_role_menu(role_id, menu_id) values (3, 1001);
-insert into sys_role_menu(role_id, menu_id) values (3, 1002);
-insert into sys_role_menu(role_id, menu_id) values (3, 1003);
-insert into sys_role_menu(role_id, menu_id) values (3, 1004);
-insert into sys_role_menu(role_id, menu_id) values (3, 1005);
-insert into sys_role_menu(role_id, menu_id) values (3, 1006);
-insert into sys_role_menu(role_id, menu_id) values (3, 1007);
-insert into sys_role_menu(role_id, menu_id) values (3, 1008);
-insert into sys_role_menu(role_id, menu_id) values (3, 1009);
-insert into sys_role_menu(role_id, menu_id) values (3, 1010);
-insert into sys_role_menu(role_id, menu_id) values (3, 1011);
-insert into sys_role_menu(role_id, menu_id) values (3, 1012);
-insert into sys_role_menu(role_id, menu_id) values (3, 1013);
-insert into sys_role_menu(role_id, menu_id) values (3, 1014);
-insert into sys_role_menu(role_id, menu_id) values (3, 1015);
-insert into sys_role_menu(role_id, menu_id) values (3, 1016);
-insert into sys_role_menu(role_id, menu_id) values (3, 1017);
-insert into sys_role_menu(role_id, menu_id) values (3, 1018);
-insert into sys_role_menu(role_id, menu_id) values (3, 1019);
-insert into sys_role_menu(role_id, menu_id) values (3, 1020);
-insert into sys_role_menu(role_id, menu_id) values (3, 1021);
-insert into sys_role_menu(role_id, menu_id) values (3, 1022);
-insert into sys_role_menu(role_id, menu_id) values (3, 1023);
-insert into sys_role_menu(role_id, menu_id) values (3, 1024);
-insert into sys_role_menu(role_id, menu_id) values (3, 1025);
-insert into sys_role_menu(role_id, menu_id) values (3, 1026);
-insert into sys_role_menu(role_id, menu_id) values (3, 1027);
-insert into sys_role_menu(role_id, menu_id) values (3, 1028);
-insert into sys_role_menu(role_id, menu_id) values (3, 1029);
-insert into sys_role_menu(role_id, menu_id) values (3, 1030);
-insert into sys_role_menu(role_id, menu_id) values (3, 1031);
-insert into sys_role_menu(role_id, menu_id) values (3, 1032);
-insert into sys_role_menu(role_id, menu_id) values (3, 1033);
-insert into sys_role_menu(role_id, menu_id) values (3, 1034);
-insert into sys_role_menu(role_id, menu_id) values (3, 1035);
-insert into sys_role_menu(role_id, menu_id) values (3, 1036);
-insert into sys_role_menu(role_id, menu_id) values (3, 1037);
-insert into sys_role_menu(role_id, menu_id) values (3, 1038);
-insert into sys_role_menu(role_id, menu_id) values (3, 1039);
-insert into sys_role_menu(role_id, menu_id) values (3, 1040);
-insert into sys_role_menu(role_id, menu_id) values (3, 1041);
-insert into sys_role_menu(role_id, menu_id) values (3, 1042);
-insert into sys_role_menu(role_id, menu_id) values (3, 1043);
-insert into sys_role_menu(role_id, menu_id) values (3, 1044);
-insert into sys_role_menu(role_id, menu_id) values (3, 1045);
-insert into sys_role_menu(role_id, menu_id) values (3, 1500);
-insert into sys_role_menu(role_id, menu_id) values (3, 1501);
-insert into sys_role_menu(role_id, menu_id) values (3, 1502);
-insert into sys_role_menu(role_id, menu_id) values (3, 1503);
-insert into sys_role_menu(role_id, menu_id) values (3, 1504);
-insert into sys_role_menu(role_id, menu_id) values (3, 1505);
-insert into sys_role_menu(role_id, menu_id) values (3, 1506);
-insert into sys_role_menu(role_id, menu_id) values (3, 1507);
-insert into sys_role_menu(role_id, menu_id) values (3, 1508);
-insert into sys_role_menu(role_id, menu_id) values (3, 1509);
-insert into sys_role_menu(role_id, menu_id) values (3, 1510);
-insert into sys_role_menu(role_id, menu_id) values (3, 1511);
-insert into sys_role_menu(role_id, menu_id) values (4, 5);
-insert into sys_role_menu(role_id, menu_id) values (4, 1500);
-insert into sys_role_menu(role_id, menu_id) values (4, 1501);
-insert into sys_role_menu(role_id, menu_id) values (4, 1502);
-insert into sys_role_menu(role_id, menu_id) values (4, 1503);
-insert into sys_role_menu(role_id, menu_id) values (4, 1504);
-insert into sys_role_menu(role_id, menu_id) values (4, 1505);
-insert into sys_role_menu(role_id, menu_id) values (4, 1506);
-insert into sys_role_menu(role_id, menu_id) values (4, 1507);
-insert into sys_role_menu(role_id, menu_id) values (4, 1508);
-insert into sys_role_menu(role_id, menu_id) values (4, 1509);
-insert into sys_role_menu(role_id, menu_id) values (4, 1510);
-insert into sys_role_menu(role_id, menu_id) values (4, 1511);
-
-insert into sys_user_role(user_id, role_id) values (3, 3);
-insert into sys_user_role(user_id, role_id) values (4, 4);
-
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (1, '000000', 102, 4, 1, '娴嬭瘯鏁版嵁鏉冮檺', '娴嬭瘯', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (2, '000000', 102, 3, 2, '瀛愯妭鐐�1', '111', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (3, '000000', 102, 3, 3, '瀛愯妭鐐�2', '222', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (4, '000000', 108, 4, 4, '娴嬭瘯鏁版嵁', 'demo', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (5, '000000', 108, 3, 13, '瀛愯妭鐐�11', '1111', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (6, '000000', 108, 3, 12, '瀛愯妭鐐�22', '2222', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (7, '000000', 108, 3, 11, '瀛愯妭鐐�33', '3333', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (8, '000000', 108, 3, 10, '瀛愯妭鐐�44', '4444', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (9, '000000', 108, 3, 9, '瀛愯妭鐐�55', '5555', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (10, '000000', 108, 3, 8, '瀛愯妭鐐�66', '6666', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (11, '000000', 108, 3, 7, '瀛愯妭鐐�77', '7777', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (12, '000000', 108, 3, 6, '瀛愯妭鐐�88', '8888', 0, 103, sysdate, 1, null, null, 0);
-insert into test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (13, '000000', 108, 3, 5, '瀛愯妭鐐�99', '9999', 0, 103, sysdate, 1, null, null, 0);
-
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (1, '000000', 0, 102, 4, '娴嬭瘯鏁版嵁鏉冮檺', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (2, '000000', 1, 102, 3, '瀛愯妭鐐�1', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (3, '000000', 2, 102, 3, '瀛愯妭鐐�2', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (4, '000000', 0, 108, 4, '娴嬭瘯鏍�1', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (5, '000000', 4, 108, 3, '瀛愯妭鐐�11', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (6, '000000', 4, 108, 3, '瀛愯妭鐐�22', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (7, '000000', 4, 108, 3, '瀛愯妭鐐�33', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (8, '000000', 5, 108, 3, '瀛愯妭鐐�44', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (9, '000000', 6, 108, 3, '瀛愯妭鐐�55', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (10, '000000', 7, 108, 3, '瀛愯妭鐐�66', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (11, '000000', 7, 108, 3, '瀛愯妭鐐�77', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (12, '000000', 10, 108, 3, '瀛愯妭鐐�88', 0, 103, sysdate, 1, null, null, 0);
-insert into test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) values (13, '000000', 10, 108, 3, '瀛愯妭鐐�99', 0, 103, sysdate, 1, null, null, 0);
diff --git a/script/sql/oracle/powerjob.sql b/script/sql/oracle/powerjob.sql
deleted file mode 100644
index 7a5419d..0000000
--- a/script/sql/oracle/powerjob.sql
+++ /dev/null
@@ -1,694 +0,0 @@
--- ----------------------------
--- Table structure for PJ_APP_INFO
--- ----------------------------
-CREATE TABLE "PJ_APP_INFO" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "APP_NAME" VARCHAR2(255 CHAR) VISIBLE ,
- "CURRENT_SERVER" VARCHAR2(255 CHAR) VISIBLE ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE ,
- "PASSWORD" VARCHAR2(255 CHAR) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Records of "PJ_APP_INFO"
--- ----------------------------
-INSERT INTO "PJ_APP_INFO" VALUES ('1', 'ruoyi-worker', '127.0.0.1:10010', NULL, NULL, '123456');
-
--- ----------------------------
--- Table structure for PJ_CONTAINER_INFO
--- ----------------------------
-CREATE TABLE "PJ_CONTAINER_INFO" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "APP_ID" NUMBER(19) VISIBLE ,
- "CONTAINER_NAME" VARCHAR2(255 CHAR) VISIBLE ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE ,
- "LAST_DEPLOY_TIME" TIMESTAMP(6) VISIBLE ,
- "SOURCE_INFO" VARCHAR2(255 CHAR) VISIBLE ,
- "SOURCE_TYPE" NUMBER(10) VISIBLE ,
- "STATUS" NUMBER(10) VISIBLE ,
- "VERSION" VARCHAR2(255 CHAR) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Table structure for PJ_INSTANCE_INFO
--- ----------------------------
-CREATE TABLE "PJ_INSTANCE_INFO" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "ACTUAL_TRIGGER_TIME" NUMBER(19) VISIBLE ,
- "APP_ID" NUMBER(19) VISIBLE ,
- "EXPECTED_TRIGGER_TIME" NUMBER(19) VISIBLE ,
- "FINISHED_TIME" NUMBER(19) VISIBLE ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE ,
- "INSTANCE_ID" NUMBER(19) VISIBLE ,
- "INSTANCE_PARAMS" CLOB VISIBLE ,
- "JOB_ID" NUMBER(19) VISIBLE ,
- "JOB_PARAMS" CLOB VISIBLE ,
- "LAST_REPORT_TIME" NUMBER(19) VISIBLE ,
- "RESULT" CLOB VISIBLE ,
- "RUNNING_TIMES" NUMBER(19) VISIBLE ,
- "STATUS" NUMBER(10) VISIBLE ,
- "TASK_TRACKER_ADDRESS" VARCHAR2(255 CHAR) VISIBLE ,
- "TYPE" NUMBER(10) VISIBLE ,
- "WF_INSTANCE_ID" NUMBER(19) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Table structure for PJ_JOB_INFO
--- ----------------------------
-CREATE TABLE "PJ_JOB_INFO" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "ALARM_CONFIG" VARCHAR2(255 CHAR) VISIBLE ,
- "APP_ID" NUMBER(19) VISIBLE ,
- "CONCURRENCY" NUMBER(10) VISIBLE ,
- "DESIGNATED_WORKERS" VARCHAR2(255 CHAR) VISIBLE ,
- "DISPATCH_STRATEGY" NUMBER(10) VISIBLE ,
- "EXECUTE_TYPE" NUMBER(10) VISIBLE ,
- "EXTRA" VARCHAR2(255 CHAR) VISIBLE ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE ,
- "INSTANCE_RETRY_NUM" NUMBER(10) VISIBLE ,
- "INSTANCE_TIME_LIMIT" NUMBER(19) VISIBLE ,
- "JOB_DESCRIPTION" VARCHAR2(255 CHAR) VISIBLE ,
- "JOB_NAME" VARCHAR2(255 CHAR) VISIBLE ,
- "JOB_PARAMS" CLOB VISIBLE ,
- "LIFECYCLE" VARCHAR2(255 CHAR) VISIBLE ,
- "LOG_CONFIG" VARCHAR2(255 CHAR) VISIBLE ,
- "MAX_INSTANCE_NUM" NUMBER(10) VISIBLE ,
- "MAX_WORKER_COUNT" NUMBER(10) VISIBLE ,
- "MIN_CPU_CORES" FLOAT(126) VISIBLE NOT NULL ,
- "MIN_DISK_SPACE" FLOAT(126) VISIBLE NOT NULL ,
- "MIN_MEMORY_SPACE" FLOAT(126) VISIBLE NOT NULL ,
- "NEXT_TRIGGER_TIME" NUMBER(19) VISIBLE ,
- "NOTIFY_USER_IDS" VARCHAR2(255 CHAR) VISIBLE ,
- "PROCESSOR_INFO" VARCHAR2(255 CHAR) VISIBLE ,
- "PROCESSOR_TYPE" NUMBER(10) VISIBLE ,
- "STATUS" NUMBER(10) VISIBLE ,
- "TAG" VARCHAR2(255 CHAR) VISIBLE ,
- "TASK_RETRY_NUM" NUMBER(10) VISIBLE ,
- "TIME_EXPRESSION" VARCHAR2(255 CHAR) VISIBLE ,
- "TIME_EXPRESSION_TYPE" NUMBER(10) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Records of "PJ_JOB_INFO"
--- ----------------------------
-INSERT INTO "PJ_JOB_INFO" VALUES ('1', '{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', '1', '5', NULL, '2', '1', NULL, NULL, NULL, '1', '0', NULL, '鍗曟満澶勭悊鍣ㄦ墽琛屾祴璇�', NULL, '{}', '{"type":1}', '0', '0', '0.0000000000000000', '0.0000000000000000', '0.0000000000000000', NULL, NULL, 'org.dromara.job.processors.StandaloneProcessorDemo', '1', '2', NULL, '1', '30000', '3');
-INSERT INTO "PJ_JOB_INFO" VALUES ('2', '{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', '1', '5', NULL, '1', '2', NULL, NULL, NULL, '0', '0', NULL, '骞挎挱澶勭悊鍣ㄦ祴璇�', NULL, '{}', '{"type":1}', '0', '0', '0.0000000000000000', '0.0000000000000000', '0.0000000000000000', NULL, NULL, 'org.dromara.job.processors.BroadcastProcessorDemo', '1', '2', NULL, '1', '30000', '3');
-INSERT INTO "PJ_JOB_INFO" VALUES ('3', '{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', '1', '5', NULL, '1', '4', NULL, NULL, NULL, '0', '0', NULL, 'Map澶勭悊鍣ㄦ祴璇�', NULL, '{}', '{"type":1}', '0', '0', '0.0000000000000000', '0.0000000000000000', '0.0000000000000000', NULL, NULL, 'org.dromara.job.processors.MapProcessorDemo', '1', '2', NULL, '1', '1000', '3');
-INSERT INTO "PJ_JOB_INFO" VALUES ('4', '{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', '1', '5', NULL, '1', '3', NULL, NULL, NULL, '0', '0', NULL, 'MapReduce澶勭悊鍣ㄦ祴璇�', NULL, '{}', '{"type":1}', '0', '0', '0.0000000000000000', '0.0000000000000000', '0.0000000000000000', NULL, NULL, 'org.dromara.job.processors.MapReduceProcessorDemo', '1', '2', NULL, '1', '1000', '3');
-
--- ----------------------------
--- Table structure for PJ_OMS_LOCK
--- ----------------------------
-CREATE TABLE "PJ_OMS_LOCK" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE ,
- "LOCK_NAME" VARCHAR2(255 CHAR) VISIBLE ,
- "MAX_LOCK_TIME" NUMBER(19) VISIBLE ,
- "OWNERIP" VARCHAR2(255 CHAR) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Table structure for PJ_SERVER_INFO
--- ----------------------------
-CREATE TABLE "PJ_SERVER_INFO" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE ,
- "IP" VARCHAR2(255 CHAR) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Table structure for PJ_USER_INFO
--- ----------------------------
-CREATE TABLE "PJ_USER_INFO" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "EMAIL" VARCHAR2(255 CHAR) VISIBLE ,
- "EXTRA" VARCHAR2(255 CHAR) VISIBLE ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE ,
- "PASSWORD" VARCHAR2(255 CHAR) VISIBLE ,
- "PHONE" VARCHAR2(255 CHAR) VISIBLE ,
- "USERNAME" VARCHAR2(255 CHAR) VISIBLE ,
- "WEB_HOOK" VARCHAR2(255 CHAR) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Table structure for PJ_WORKFLOW_INFO
--- ----------------------------
-CREATE TABLE "PJ_WORKFLOW_INFO" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "APP_ID" NUMBER(19) VISIBLE ,
- "EXTRA" VARCHAR2(255 CHAR) VISIBLE ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE ,
- "LIFECYCLE" VARCHAR2(255 CHAR) VISIBLE ,
- "MAX_WF_INSTANCE_NUM" NUMBER(10) VISIBLE ,
- "NEXT_TRIGGER_TIME" NUMBER(19) VISIBLE ,
- "NOTIFY_USER_IDS" VARCHAR2(255 CHAR) VISIBLE ,
- "PEDAG" CLOB VISIBLE ,
- "STATUS" NUMBER(10) VISIBLE ,
- "TIME_EXPRESSION" VARCHAR2(255 CHAR) VISIBLE ,
- "TIME_EXPRESSION_TYPE" NUMBER(10) VISIBLE ,
- "WF_DESCRIPTION" VARCHAR2(255 CHAR) VISIBLE ,
- "WF_NAME" VARCHAR2(255 CHAR) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Table structure for PJ_WORKFLOW_INSTANCE_INFO
--- ----------------------------
-CREATE TABLE "PJ_WORKFLOW_INSTANCE_INFO" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "ACTUAL_TRIGGER_TIME" NUMBER(19) VISIBLE ,
- "APP_ID" NUMBER(19) VISIBLE ,
- "DAG" CLOB VISIBLE ,
- "EXPECTED_TRIGGER_TIME" NUMBER(19) VISIBLE ,
- "FINISHED_TIME" NUMBER(19) VISIBLE ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE ,
- "PARENT_WF_INSTANCE_ID" NUMBER(19) VISIBLE ,
- "RESULT" CLOB VISIBLE ,
- "STATUS" NUMBER(10) VISIBLE ,
- "WF_CONTEXT" CLOB VISIBLE ,
- "WF_INIT_PARAMS" CLOB VISIBLE ,
- "WF_INSTANCE_ID" NUMBER(19) VISIBLE ,
- "WORKFLOW_ID" NUMBER(19) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Table structure for PJ_WORKFLOW_NODE_INFO
--- ----------------------------
-CREATE TABLE "PJ_WORKFLOW_NODE_INFO" (
- "ID" NUMBER(19) VISIBLE NOT NULL ,
- "APP_ID" NUMBER(19) VISIBLE NOT NULL ,
- "ENABLE" NUMBER(1) VISIBLE NOT NULL ,
- "EXTRA" CLOB VISIBLE ,
- "GMT_CREATE" TIMESTAMP(6) VISIBLE NOT NULL ,
- "GMT_MODIFIED" TIMESTAMP(6) VISIBLE NOT NULL ,
- "JOB_ID" NUMBER(19) VISIBLE ,
- "NODE_NAME" VARCHAR2(255 CHAR) VISIBLE ,
- "NODE_PARAMS" CLOB VISIBLE ,
- "SKIP_WHEN_FAILED" NUMBER(1) VISIBLE NOT NULL ,
- "TYPE" NUMBER(10) VISIBLE ,
- "WORKFLOW_ID" NUMBER(19) VISIBLE
-)
-TABLESPACE "ROOT"
-LOGGING
-NOCOMPRESS
-PCTFREE 10
-INITRANS 1
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
-)
-PARALLEL 1
-NOCACHE
-DISABLE ROW MOVEMENT
-;
-
--- ----------------------------
--- Primary Key structure for table PJ_APP_INFO
--- ----------------------------
-ALTER TABLE "PJ_APP_INFO" ADD CONSTRAINT "SYS_C0012204" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Uniques structure for table PJ_APP_INFO
--- ----------------------------
-ALTER TABLE "PJ_APP_INFO" ADD CONSTRAINT "UIDX01_APP_INFO" UNIQUE ("APP_NAME") NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Checks structure for table PJ_APP_INFO
--- ----------------------------
-ALTER TABLE "PJ_APP_INFO" ADD CONSTRAINT "SYS_C0012203" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Primary Key structure for table PJ_CONTAINER_INFO
--- ----------------------------
-ALTER TABLE "PJ_CONTAINER_INFO" ADD CONSTRAINT "SYS_C0012206" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Checks structure for table PJ_CONTAINER_INFO
--- ----------------------------
-ALTER TABLE "PJ_CONTAINER_INFO" ADD CONSTRAINT "SYS_C0012205" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Indexes structure for table PJ_CONTAINER_INFO
--- ----------------------------
-CREATE INDEX "IDX01_CONTAINER_INFO"
- ON "PJ_CONTAINER_INFO" ("APP_ID" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-
--- ----------------------------
--- Primary Key structure for table PJ_INSTANCE_INFO
--- ----------------------------
-ALTER TABLE "PJ_INSTANCE_INFO" ADD CONSTRAINT "SYS_C0012208" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Checks structure for table PJ_INSTANCE_INFO
--- ----------------------------
-ALTER TABLE "PJ_INSTANCE_INFO" ADD CONSTRAINT "SYS_C0012207" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Indexes structure for table PJ_INSTANCE_INFO
--- ----------------------------
-CREATE INDEX "IDX01_INSTANCE_INFO"
- ON "PJ_INSTANCE_INFO" ("JOB_ID" ASC, "STATUS" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-CREATE INDEX "IDX02_INSTANCE_INFO"
- ON "PJ_INSTANCE_INFO" ("APP_ID" ASC, "STATUS" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-CREATE INDEX "IDX03_INSTANCE_INFO"
- ON "PJ_INSTANCE_INFO" ("INSTANCE_ID" ASC, "STATUS" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-
--- ----------------------------
--- Primary Key structure for table PJ_JOB_INFO
--- ----------------------------
-ALTER TABLE "PJ_JOB_INFO" ADD CONSTRAINT "SYS_C0012213" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Checks structure for table PJ_JOB_INFO
--- ----------------------------
-ALTER TABLE "PJ_JOB_INFO" ADD CONSTRAINT "SYS_C0012209" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-ALTER TABLE "PJ_JOB_INFO" ADD CONSTRAINT "SYS_C0012210" CHECK ("MIN_CPU_CORES" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-ALTER TABLE "PJ_JOB_INFO" ADD CONSTRAINT "SYS_C0012211" CHECK ("MIN_DISK_SPACE" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-ALTER TABLE "PJ_JOB_INFO" ADD CONSTRAINT "SYS_C0012212" CHECK ("MIN_MEMORY_SPACE" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Indexes structure for table PJ_JOB_INFO
--- ----------------------------
-CREATE INDEX "IDX01_JOB_INFO"
- ON "PJ_JOB_INFO" ("APP_ID" ASC, "NEXT_TRIGGER_TIME" ASC, "TIME_EXPRESSION_TYPE" ASC, "STATUS" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-
--- ----------------------------
--- Primary Key structure for table PJ_OMS_LOCK
--- ----------------------------
-ALTER TABLE "PJ_OMS_LOCK" ADD CONSTRAINT "SYS_C0012215" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Uniques structure for table PJ_OMS_LOCK
--- ----------------------------
-ALTER TABLE "PJ_OMS_LOCK" ADD CONSTRAINT "UIDX01_OMS_LOCK" UNIQUE ("LOCK_NAME") NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Checks structure for table PJ_OMS_LOCK
--- ----------------------------
-ALTER TABLE "PJ_OMS_LOCK" ADD CONSTRAINT "SYS_C0012214" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Primary Key structure for table PJ_SERVER_INFO
--- ----------------------------
-ALTER TABLE "PJ_SERVER_INFO" ADD CONSTRAINT "SYS_C0012217" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Uniques structure for table PJ_SERVER_INFO
--- ----------------------------
-ALTER TABLE "PJ_SERVER_INFO" ADD CONSTRAINT "UIDX01_SERVER_INFO" UNIQUE ("IP") NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Checks structure for table PJ_SERVER_INFO
--- ----------------------------
-ALTER TABLE "PJ_SERVER_INFO" ADD CONSTRAINT "SYS_C0012216" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Indexes structure for table PJ_SERVER_INFO
--- ----------------------------
-CREATE INDEX "IDX01_SERVER_INFO"
- ON "PJ_SERVER_INFO" ("GMT_MODIFIED" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-
--- ----------------------------
--- Primary Key structure for table PJ_USER_INFO
--- ----------------------------
-ALTER TABLE "PJ_USER_INFO" ADD CONSTRAINT "SYS_C0012219" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Checks structure for table PJ_USER_INFO
--- ----------------------------
-ALTER TABLE "PJ_USER_INFO" ADD CONSTRAINT "SYS_C0012218" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Indexes structure for table PJ_USER_INFO
--- ----------------------------
-CREATE INDEX "UIDX01_USER_INFO"
- ON "PJ_USER_INFO" ("USERNAME" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-CREATE INDEX "UIDX02_USER_INFO"
- ON "PJ_USER_INFO" ("EMAIL" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-
--- ----------------------------
--- Primary Key structure for table PJ_WORKFLOW_INFO
--- ----------------------------
-ALTER TABLE "PJ_WORKFLOW_INFO" ADD CONSTRAINT "SYS_C0012221" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Checks structure for table PJ_WORKFLOW_INFO
--- ----------------------------
-ALTER TABLE "PJ_WORKFLOW_INFO" ADD CONSTRAINT "SYS_C0012220" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Indexes structure for table PJ_WORKFLOW_INFO
--- ----------------------------
-CREATE INDEX "IDX01_WORKFLOW_INFO"
- ON "PJ_WORKFLOW_INFO" ("APP_ID" ASC, "NEXT_TRIGGER_TIME" ASC, "TIME_EXPRESSION_TYPE" ASC, "STATUS" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-
--- ----------------------------
--- Primary Key structure for table PJ_WORKFLOW_INSTANCE_INFO
--- ----------------------------
-ALTER TABLE "PJ_WORKFLOW_INSTANCE_INFO" ADD CONSTRAINT "SYS_C0012223" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Uniques structure for table PJ_WORKFLOW_INSTANCE_INFO
--- ----------------------------
-ALTER TABLE "PJ_WORKFLOW_INSTANCE_INFO" ADD CONSTRAINT "UIDX01_WF_INSTANCE" UNIQUE ("WF_INSTANCE_ID") NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Checks structure for table PJ_WORKFLOW_INSTANCE_INFO
--- ----------------------------
-ALTER TABLE "PJ_WORKFLOW_INSTANCE_INFO" ADD CONSTRAINT "SYS_C0012222" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Indexes structure for table PJ_WORKFLOW_INSTANCE_INFO
--- ----------------------------
-CREATE INDEX "IDX01_WF_INSTANCE"
- ON "PJ_WORKFLOW_INSTANCE_INFO" ("WORKFLOW_ID" ASC, "EXPECTED_TRIGGER_TIME" ASC, "APP_ID" ASC, "STATUS" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
-
--- ----------------------------
--- Primary Key structure for table PJ_WORKFLOW_NODE_INFO
--- ----------------------------
-ALTER TABLE "PJ_WORKFLOW_NODE_INFO" ADD CONSTRAINT "SYS_C0012230" PRIMARY KEY ("ID");
-
--- ----------------------------
--- Checks structure for table PJ_WORKFLOW_NODE_INFO
--- ----------------------------
-ALTER TABLE "PJ_WORKFLOW_NODE_INFO" ADD CONSTRAINT "SYS_C0012224" CHECK ("ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-ALTER TABLE "PJ_WORKFLOW_NODE_INFO" ADD CONSTRAINT "SYS_C0012225" CHECK ("APP_ID" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-ALTER TABLE "PJ_WORKFLOW_NODE_INFO" ADD CONSTRAINT "SYS_C0012226" CHECK ("ENABLE" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-ALTER TABLE "PJ_WORKFLOW_NODE_INFO" ADD CONSTRAINT "SYS_C0012227" CHECK ("GMT_CREATE" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-ALTER TABLE "PJ_WORKFLOW_NODE_INFO" ADD CONSTRAINT "SYS_C0012228" CHECK ("GMT_MODIFIED" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-ALTER TABLE "PJ_WORKFLOW_NODE_INFO" ADD CONSTRAINT "SYS_C0012229" CHECK ("SKIP_WHEN_FAILED" IS NOT NULL) NOT DEFERRABLE INITIALLY IMMEDIATE NORELY VALIDATE;
-
--- ----------------------------
--- Indexes structure for table PJ_WORKFLOW_NODE_INFO
--- ----------------------------
-CREATE INDEX "IDX01_WORKFLOW_NODE_INFO"
- ON "PJ_WORKFLOW_NODE_INFO" ("GMT_CREATE" ASC, "WORKFLOW_ID" ASC)
- LOGGING
- TABLESPACE "ROOT"
- VISIBLE
-PCTFREE 10
-INITRANS 2
-STORAGE (
- INITIAL 65536
- NEXT 1048576
- MINEXTENTS 1
- MAXEXTENTS 2147483645
- BUFFER_POOL DEFAULT
- FLASH_CACHE DEFAULT
-)
- USABLE;
diff --git a/script/sql/oracle/snail_job_oracle.sql b/script/sql/oracle/snail_job_oracle.sql
new file mode 100644
index 0000000..19aa07e
--- /dev/null
+++ b/script/sql/oracle/snail_job_oracle.sql
@@ -0,0 +1,894 @@
+/*
+ SnailJob Database Transfer Tool
+ Source Server Type : MySQL
+ Target Server Type : Oracle
+ Date: 2024-05-14 23:36:38
+*/
+
+
+-- sj_namespace
+CREATE TABLE sj_namespace
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ name varchar2(64) NULL,
+ unique_id varchar2(64) NULL,
+ description varchar2(256) DEFAULT '' NULL,
+ deleted smallint DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_namespace
+ ADD CONSTRAINT pk_sj_namespace PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_namespace_01 ON sj_namespace (name);
+
+COMMENT ON COLUMN sj_namespace.id IS '涓婚敭';
+COMMENT ON COLUMN sj_namespace.name IS '鍚嶇О';
+COMMENT ON COLUMN sj_namespace.unique_id IS '鍞竴id';
+COMMENT ON COLUMN sj_namespace.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_namespace.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_namespace.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_namespace.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_namespace IS '鍛藉悕绌洪棿';
+
+INSERT INTO sj_namespace(name, unique_id, description, deleted, create_dt, update_dt) VALUES ('Development', 'dev', '', 0, sysdate, sysdate);
+INSERT INTO sj_namespace(name, unique_id, description, deleted, create_dt, update_dt) VALUES ('Production', 'prod', '', 0, sysdate, sysdate);
+
+-- sj_group_config
+CREATE TABLE sj_group_config
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) DEFAULT '' NULL,
+ description varchar2(256) DEFAULT '' NULL,
+ token varchar2(64) DEFAULT 'SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT' NULL,
+ group_status smallint DEFAULT 0 NOT NULL,
+ version number NOT NULL,
+ group_partition number NOT NULL,
+ id_generator_mode smallint DEFAULT 1 NOT NULL,
+ init_scene smallint DEFAULT 0 NOT NULL,
+ bucket_index number DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_group_config
+ ADD CONSTRAINT pk_sj_group_config PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX uk_sj_group_config_01 ON sj_group_config (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_group_config.id IS '涓婚敭';
+COMMENT ON COLUMN sj_group_config.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_group_config.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_group_config.description IS '缁勬弿杩�';
+COMMENT ON COLUMN sj_group_config.token IS 'token';
+COMMENT ON COLUMN sj_group_config.group_status IS '缁勭姸鎬� 0銆佹湭鍚敤 1銆佸惎鐢�';
+COMMENT ON COLUMN sj_group_config.version IS '鐗堟湰鍙�';
+COMMENT ON COLUMN sj_group_config.group_partition IS '鍒嗗尯';
+COMMENT ON COLUMN sj_group_config.id_generator_mode IS '鍞竴id鐢熸垚妯″紡 榛樿鍙锋妯″紡';
+COMMENT ON COLUMN sj_group_config.init_scene IS '鏄惁鍒濆鍖栧満鏅� 0:鍚� 1:鏄�';
+COMMENT ON COLUMN sj_group_config.bucket_index IS 'bucket';
+COMMENT ON COLUMN sj_group_config.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_group_config.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_group_config IS '缁勯厤缃�';
+
+INSERT INTO sj_group_config (namespace_id, group_name, description, token, group_status, version, group_partition, id_generator_mode, init_scene, bucket_index, create_dt, update_dt) VALUES ('dev', 'ruoyi_group', '', 'SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT', 1, 1, 0, 1, 1, 4, sysdate, sysdate);
+
+-- sj_notify_config
+CREATE TABLE sj_notify_config
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) NULL,
+ business_id varchar2(64) NULL,
+ system_task_type smallint DEFAULT 3 NOT NULL,
+ notify_status smallint DEFAULT 0 NOT NULL,
+ recipient_ids varchar2(128) NULL,
+ notify_threshold number DEFAULT 0 NOT NULL,
+ notify_scene smallint DEFAULT 0 NOT NULL,
+ rate_limiter_status smallint DEFAULT 0 NOT NULL,
+ rate_limiter_threshold number DEFAULT 0 NOT NULL,
+ description varchar2(256) DEFAULT '' NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_notify_config
+ ADD CONSTRAINT pk_sj_notify_config PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_notify_config_01 ON sj_notify_config (namespace_id, group_name, business_id);
+
+COMMENT ON COLUMN sj_notify_config.id IS '涓婚敭';
+COMMENT ON COLUMN sj_notify_config.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_notify_config.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_notify_config.business_id IS '涓氬姟id ( job_id鎴杦orkflow_id鎴杝cene_name ) ';
+COMMENT ON COLUMN sj_notify_config.system_task_type IS '浠诲姟绫诲瀷 1. 閲嶈瘯浠诲姟 2. 閲嶈瘯鍥炶皟 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟';
+COMMENT ON COLUMN sj_notify_config.notify_status IS '閫氱煡鐘舵�� 0銆佹湭鍚敤 1銆佸惎鐢�';
+COMMENT ON COLUMN sj_notify_config.recipient_ids IS '鎺ユ敹浜篿d鍒楄〃';
+COMMENT ON COLUMN sj_notify_config.notify_threshold IS '閫氱煡闃堝��';
+COMMENT ON COLUMN sj_notify_config.notify_scene IS '閫氱煡鍦烘櫙';
+COMMENT ON COLUMN sj_notify_config.rate_limiter_status IS '闄愭祦鐘舵�� 0銆佹湭鍚敤 1銆佸惎鐢�';
+COMMENT ON COLUMN sj_notify_config.rate_limiter_threshold IS '姣忕闄愭祦闃堝��';
+COMMENT ON COLUMN sj_notify_config.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_notify_config.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_notify_config.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_notify_config IS '閫氱煡閰嶇疆';
+
+-- sj_notify_recipient
+CREATE TABLE sj_notify_recipient
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ recipient_name varchar2(64) NULL,
+ notify_type smallint DEFAULT 0 NOT NULL,
+ notify_attribute varchar2(512) NULL,
+ description varchar2(256) DEFAULT '' NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_notify_recipient
+ ADD CONSTRAINT pk_sj_notify_recipient PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_notify_recipient_01 ON sj_notify_recipient (namespace_id);
+
+COMMENT ON COLUMN sj_notify_recipient.id IS '涓婚敭';
+COMMENT ON COLUMN sj_notify_recipient.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_notify_recipient.recipient_name IS '鎺ユ敹浜哄悕绉�';
+COMMENT ON COLUMN sj_notify_recipient.notify_type IS '閫氱煡绫诲瀷 1銆侀拤閽� 2銆侀偖浠� 3銆佷紒涓氬井淇� 4 椋炰功';
+COMMENT ON COLUMN sj_notify_recipient.notify_attribute IS '閰嶇疆灞炴��';
+COMMENT ON COLUMN sj_notify_recipient.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_notify_recipient.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_notify_recipient.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_notify_recipient IS '鍛婅閫氱煡鎺ユ敹浜�';
+
+-- sj_retry_dead_letter_0
+CREATE TABLE sj_retry_dead_letter_0
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ unique_id varchar2(64) NULL,
+ group_name varchar2(64) NULL,
+ scene_name varchar2(64) NULL,
+ idempotent_id varchar2(64) NULL,
+ biz_no varchar2(64) DEFAULT '' NULL,
+ executor_name varchar2(512) DEFAULT '' NULL,
+ args_str clob NULL,
+ ext_attrs clob NULL,
+ task_type smallint DEFAULT 1 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_retry_dead_letter_0
+ ADD CONSTRAINT pk_sj_retry_dead_letter_0 PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX uk_sj_retry_dead_letter_0_01 ON sj_retry_dead_letter_0 (namespace_id, group_name, unique_id);
+
+CREATE INDEX idx_sj_retry_dead_letter_0_01 ON sj_retry_dead_letter_0 (namespace_id, group_name, scene_name);
+CREATE INDEX idx_sj_retry_dead_letter_0_02 ON sj_retry_dead_letter_0 (idempotent_id);
+CREATE INDEX idx_sj_retry_dead_letter_0_03 ON sj_retry_dead_letter_0 (biz_no);
+CREATE INDEX idx_sj_retry_dead_letter_0_04 ON sj_retry_dead_letter_0 (create_dt);
+
+COMMENT ON COLUMN sj_retry_dead_letter_0.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_dead_letter_0.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_dead_letter_0.unique_id IS '鍚岀粍涓媔d鍞竴';
+COMMENT ON COLUMN sj_retry_dead_letter_0.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_dead_letter_0.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_dead_letter_0.idempotent_id IS '骞傜瓑id';
+COMMENT ON COLUMN sj_retry_dead_letter_0.biz_no IS '涓氬姟缂栧彿';
+COMMENT ON COLUMN sj_retry_dead_letter_0.executor_name IS '鎵ц鍣ㄥ悕绉�';
+COMMENT ON COLUMN sj_retry_dead_letter_0.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_retry_dead_letter_0.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_retry_dead_letter_0.task_type IS '浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�';
+COMMENT ON COLUMN sj_retry_dead_letter_0.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON TABLE sj_retry_dead_letter_0 IS '姝讳俊闃熷垪琛�';
+
+-- sj_retry_task_0
+CREATE TABLE sj_retry_task_0
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ unique_id varchar2(64) NULL,
+ group_name varchar2(64) NULL,
+ scene_name varchar2(64) NULL,
+ idempotent_id varchar2(64) NULL,
+ biz_no varchar2(64) DEFAULT '' NULL,
+ executor_name varchar2(512) DEFAULT '' NULL,
+ args_str clob NULL,
+ ext_attrs clob NULL,
+ next_trigger_at date NOT NULL,
+ retry_count number DEFAULT 0 NOT NULL,
+ retry_status smallint DEFAULT 0 NOT NULL,
+ task_type smallint DEFAULT 1 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_retry_task_0
+ ADD CONSTRAINT pk_sj_retry_task_0 PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX uk_sj_retry_task_0_01 ON sj_retry_task_0 (namespace_id, group_name, unique_id);
+
+CREATE INDEX idx_sj_retry_task_0_01 ON sj_retry_task_0 (namespace_id, group_name, scene_name);
+CREATE INDEX idx_sj_retry_task_0_02 ON sj_retry_task_0 (namespace_id, group_name, task_type);
+CREATE INDEX idx_sj_retry_task_0_03 ON sj_retry_task_0 (namespace_id, group_name, retry_status);
+CREATE INDEX idx_sj_retry_task_0_04 ON sj_retry_task_0 (idempotent_id);
+CREATE INDEX idx_sj_retry_task_0_05 ON sj_retry_task_0 (biz_no);
+CREATE INDEX idx_sj_retry_task_0_06 ON sj_retry_task_0 (create_dt);
+
+COMMENT ON COLUMN sj_retry_task_0.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_task_0.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_task_0.unique_id IS '鍚岀粍涓媔d鍞竴';
+COMMENT ON COLUMN sj_retry_task_0.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_task_0.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_task_0.idempotent_id IS '骞傜瓑id';
+COMMENT ON COLUMN sj_retry_task_0.biz_no IS '涓氬姟缂栧彿';
+COMMENT ON COLUMN sj_retry_task_0.executor_name IS '鎵ц鍣ㄥ悕绉�';
+COMMENT ON COLUMN sj_retry_task_0.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_retry_task_0.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_retry_task_0.next_trigger_at IS '涓嬫瑙﹀彂鏃堕棿';
+COMMENT ON COLUMN sj_retry_task_0.retry_count IS '閲嶈瘯娆℃暟';
+COMMENT ON COLUMN sj_retry_task_0.retry_status IS '閲嶈瘯鐘舵�� 0銆侀噸璇曚腑 1銆佹垚鍔� 2銆佹渶澶ч噸璇曟鏁�';
+COMMENT ON COLUMN sj_retry_task_0.task_type IS '浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�';
+COMMENT ON COLUMN sj_retry_task_0.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_retry_task_0.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_retry_task_0 IS '浠诲姟琛�';
+
+-- sj_retry_task_log
+CREATE TABLE sj_retry_task_log
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ unique_id varchar2(64) NULL,
+ group_name varchar2(64) NULL,
+ scene_name varchar2(64) NULL,
+ idempotent_id varchar2(64) NULL,
+ biz_no varchar2(64) DEFAULT '' NULL,
+ executor_name varchar2(512) DEFAULT '' NULL,
+ args_str clob NULL,
+ ext_attrs clob NULL,
+ retry_status smallint DEFAULT 0 NOT NULL,
+ task_type smallint DEFAULT 1 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_retry_task_log
+ ADD CONSTRAINT pk_sj_retry_task_log PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_retry_task_log_01 ON sj_retry_task_log (namespace_id, group_name, scene_name);
+CREATE INDEX idx_sj_retry_task_log_02 ON sj_retry_task_log (retry_status);
+CREATE INDEX idx_sj_retry_task_log_03 ON sj_retry_task_log (idempotent_id);
+CREATE INDEX idx_sj_retry_task_log_04 ON sj_retry_task_log (unique_id);
+CREATE INDEX idx_sj_retry_task_log_05 ON sj_retry_task_log (biz_no);
+CREATE INDEX idx_sj_retry_task_log_06 ON sj_retry_task_log (create_dt);
+
+COMMENT ON COLUMN sj_retry_task_log.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_task_log.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_task_log.unique_id IS '鍚岀粍涓媔d鍞竴';
+COMMENT ON COLUMN sj_retry_task_log.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_task_log.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_task_log.idempotent_id IS '骞傜瓑id';
+COMMENT ON COLUMN sj_retry_task_log.biz_no IS '涓氬姟缂栧彿';
+COMMENT ON COLUMN sj_retry_task_log.executor_name IS '鎵ц鍣ㄥ悕绉�';
+COMMENT ON COLUMN sj_retry_task_log.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_retry_task_log.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_retry_task_log.retry_status IS '閲嶈瘯鐘舵�� 0銆侀噸璇曚腑 1銆佹垚鍔� 2銆佹渶澶ф鏁�';
+COMMENT ON COLUMN sj_retry_task_log.task_type IS '浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�';
+COMMENT ON COLUMN sj_retry_task_log.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_retry_task_log.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_retry_task_log IS '浠诲姟鏃ュ織鍩虹淇℃伅琛�';
+
+-- sj_retry_task_log_message
+CREATE TABLE sj_retry_task_log_message
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) NULL,
+ unique_id varchar2(64) NULL,
+ message clob NULL,
+ log_num number DEFAULT 1 NOT NULL,
+ real_time number DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_retry_task_log_message
+ ADD CONSTRAINT pk_sj_retry_task_log_message PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_retry_task_log_message_01 ON sj_retry_task_log_message (namespace_id, group_name, unique_id);
+CREATE INDEX idx_sj_retry_task_log_message_02 ON sj_retry_task_log_message (create_dt);
+
+COMMENT ON COLUMN sj_retry_task_log_message.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_task_log_message.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_task_log_message.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_task_log_message.unique_id IS '鍚岀粍涓媔d鍞竴';
+COMMENT ON COLUMN sj_retry_task_log_message.message IS '寮傚父淇℃伅';
+COMMENT ON COLUMN sj_retry_task_log_message.log_num IS '鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_task_log_message.real_time IS '涓婃姤鏃堕棿';
+COMMENT ON COLUMN sj_retry_task_log_message.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON TABLE sj_retry_task_log_message IS '浠诲姟璋冨害鏃ュ織淇℃伅璁板綍琛�';
+
+-- sj_retry_scene_config
+CREATE TABLE sj_retry_scene_config
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ scene_name varchar2(64) NULL,
+ group_name varchar2(64) NULL,
+ scene_status smallint DEFAULT 0 NOT NULL,
+ max_retry_count number DEFAULT 5 NOT NULL,
+ back_off smallint DEFAULT 1 NOT NULL,
+ trigger_interval varchar2(16) DEFAULT '' NULL,
+ deadline_request number DEFAULT 60000 NOT NULL,
+ executor_timeout number DEFAULT 5 NOT NULL,
+ route_key smallint DEFAULT 4 NOT NULL,
+ description varchar2(256) DEFAULT '' NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_retry_scene_config
+ ADD CONSTRAINT pk_sj_retry_scene_config PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX uk_sj_retry_scene_config_01 ON sj_retry_scene_config (namespace_id, group_name, scene_name);
+
+COMMENT ON COLUMN sj_retry_scene_config.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_scene_config.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_scene_config.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_scene_config.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_scene_config.scene_status IS '缁勭姸鎬� 0銆佹湭鍚敤 1銆佸惎鐢�';
+COMMENT ON COLUMN sj_retry_scene_config.max_retry_count IS '鏈�澶ч噸璇曟鏁�';
+COMMENT ON COLUMN sj_retry_scene_config.back_off IS '1銆侀粯璁ょ瓑绾� 2銆佸浐瀹氶棿闅旀椂闂� 3銆丆RON 琛ㄨ揪寮�';
+COMMENT ON COLUMN sj_retry_scene_config.trigger_interval IS '闂撮殧鏃堕暱';
+COMMENT ON COLUMN sj_retry_scene_config.deadline_request IS 'Deadline Request 璋冪敤閾捐秴鏃� 鍗曚綅姣';
+COMMENT ON COLUMN sj_retry_scene_config.executor_timeout IS '浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇';
+COMMENT ON COLUMN sj_retry_scene_config.route_key IS '璺敱绛栫暐';
+COMMENT ON COLUMN sj_retry_scene_config.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_retry_scene_config.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_retry_scene_config.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_retry_scene_config IS '鍦烘櫙閰嶇疆';
+
+-- sj_server_node
+CREATE TABLE sj_server_node
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) NULL,
+ host_id varchar2(64) NULL,
+ host_ip varchar2(64) NULL,
+ host_port number NOT NULL,
+ expire_at date NOT NULL,
+ node_type smallint NOT NULL,
+ ext_attrs varchar2(256) DEFAULT '' NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_server_node
+ ADD CONSTRAINT pk_sj_server_node PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX uk_sj_server_node_01 ON sj_server_node (host_id, host_ip);
+
+CREATE INDEX idx_sj_server_node_01 ON sj_server_node (namespace_id, group_name);
+CREATE INDEX idx_sj_server_node_02 ON sj_server_node (expire_at, node_type);
+
+COMMENT ON COLUMN sj_server_node.id IS '涓婚敭';
+COMMENT ON COLUMN sj_server_node.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_server_node.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_server_node.host_id IS '涓绘満id';
+COMMENT ON COLUMN sj_server_node.host_ip IS '鏈哄櫒ip';
+COMMENT ON COLUMN sj_server_node.host_port IS '鏈哄櫒绔彛';
+COMMENT ON COLUMN sj_server_node.expire_at IS '杩囨湡鏃堕棿';
+COMMENT ON COLUMN sj_server_node.node_type IS '鑺傜偣绫诲瀷 1銆佸鎴风 2銆佹槸鏈嶅姟绔�';
+COMMENT ON COLUMN sj_server_node.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_server_node.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_server_node.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_server_node IS '鏈嶅姟鍣ㄨ妭鐐�';
+
+-- sj_distributed_lock
+CREATE TABLE sj_distributed_lock
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ name varchar2(64) NULL,
+ lock_until timestamp(3) DEFAULT CURRENT_TIMESTAMP(3) NOT NULL,
+ locked_at timestamp(3) DEFAULT CURRENT_TIMESTAMP(3) NOT NULL,
+ locked_by varchar2(255) NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_distributed_lock
+ ADD CONSTRAINT pk_sj_distributed_lock PRIMARY KEY (id);
+
+COMMENT ON COLUMN sj_distributed_lock.id IS '涓婚敭';
+COMMENT ON COLUMN sj_distributed_lock.name IS '閿佸悕绉�';
+COMMENT ON COLUMN sj_distributed_lock.lock_until IS '閿佸畾鏃堕暱';
+COMMENT ON COLUMN sj_distributed_lock.locked_at IS '閿佸畾鏃堕棿';
+COMMENT ON COLUMN sj_distributed_lock.locked_by IS '閿佸畾鑰�';
+COMMENT ON COLUMN sj_distributed_lock.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_distributed_lock.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_distributed_lock IS '閿佸畾琛�';
+
+-- sj_system_user
+CREATE TABLE sj_system_user
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ username varchar2(64) NULL,
+ password varchar2(128) NULL,
+ role smallint DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_system_user
+ ADD CONSTRAINT pk_sj_system_user PRIMARY KEY (id);
+
+COMMENT ON COLUMN sj_system_user.id IS '涓婚敭';
+COMMENT ON COLUMN sj_system_user.username IS '璐﹀彿';
+COMMENT ON COLUMN sj_system_user.password IS '瀵嗙爜';
+COMMENT ON COLUMN sj_system_user.role IS '瑙掕壊锛�1-鏅�氱敤鎴枫��2-绠$悊鍛�';
+COMMENT ON COLUMN sj_system_user.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_system_user.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_system_user IS '绯荤粺鐢ㄦ埛琛�';
+
+-- pwd: admin
+INSERT INTO sj_system_user(username, password, role, create_dt, update_dt) VALUES ('admin', '465c194afb65670f38322df087f0a9bb225cc257e43eb4ac5a0c98ef5b3173ac', 2, sysdate, sysdate);
+
+-- sj_system_user_permission
+CREATE TABLE sj_system_user_permission
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ group_name varchar2(64) NULL,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ system_user_id number NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_system_user_permission
+ ADD CONSTRAINT pk_sj_system_user_permission PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX uk_sj_system_user_permission_01 ON sj_system_user_permission (namespace_id, group_name, system_user_id);
+
+COMMENT ON COLUMN sj_system_user_permission.id IS '涓婚敭';
+COMMENT ON COLUMN sj_system_user_permission.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_system_user_permission.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_system_user_permission.system_user_id IS '绯荤粺鐢ㄦ埛id';
+COMMENT ON COLUMN sj_system_user_permission.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_system_user_permission.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_system_user_permission IS '绯荤粺鐢ㄦ埛鏉冮檺琛�';
+
+-- sj_sequence_alloc
+CREATE TABLE sj_sequence_alloc
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) DEFAULT '' NULL,
+ max_id number DEFAULT 1 NOT NULL,
+ step number DEFAULT 100 NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_sequence_alloc
+ ADD CONSTRAINT pk_sj_sequence_alloc PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX uk_sj_sequence_alloc_01 ON sj_sequence_alloc (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_sequence_alloc.id IS '涓婚敭';
+COMMENT ON COLUMN sj_sequence_alloc.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_sequence_alloc.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_sequence_alloc.max_id IS '鏈�澶d';
+COMMENT ON COLUMN sj_sequence_alloc.step IS '姝ラ暱';
+COMMENT ON COLUMN sj_sequence_alloc.update_dt IS '鏇存柊鏃堕棿';
+COMMENT ON TABLE sj_sequence_alloc IS '鍙锋妯″紡搴忓彿ID鍒嗛厤琛�';
+
+-- sj_job
+CREATE TABLE sj_job
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) NULL,
+ job_name varchar2(64) NULL,
+ args_str clob DEFAULT NULL NULL,
+ args_type smallint DEFAULT 1 NOT NULL,
+ next_trigger_at number NOT NULL,
+ job_status smallint DEFAULT 1 NOT NULL,
+ task_type smallint DEFAULT 1 NOT NULL,
+ route_key smallint DEFAULT 4 NOT NULL,
+ executor_type smallint DEFAULT 1 NOT NULL,
+ executor_info varchar2(255) DEFAULT NULL NULL,
+ trigger_type smallint NOT NULL,
+ trigger_interval varchar2(255) NULL,
+ block_strategy smallint DEFAULT 1 NOT NULL,
+ executor_timeout number DEFAULT 0 NOT NULL,
+ max_retry_times number DEFAULT 0 NOT NULL,
+ parallel_num number DEFAULT 1 NOT NULL,
+ retry_interval number DEFAULT 0 NOT NULL,
+ bucket_index number DEFAULT 0 NOT NULL,
+ resident smallint DEFAULT 0 NOT NULL,
+ description varchar2(256) DEFAULT '' NULL,
+ ext_attrs varchar2(256) DEFAULT '' NULL,
+ deleted smallint DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_job
+ ADD CONSTRAINT pk_sj_job PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_job_01 ON sj_job (namespace_id, group_name);
+CREATE INDEX idx_sj_job_02 ON sj_job (job_status, bucket_index);
+CREATE INDEX idx_sj_job_03 ON sj_job (create_dt);
+
+COMMENT ON COLUMN sj_job.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job.job_name IS '鍚嶇О';
+COMMENT ON COLUMN sj_job.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_job.args_type IS '鍙傛暟绫诲瀷 ';
+COMMENT ON COLUMN sj_job.next_trigger_at IS '涓嬫瑙﹀彂鏃堕棿';
+COMMENT ON COLUMN sj_job.job_status IS '浠诲姟鐘舵�� 0銆佸叧闂��1銆佸紑鍚�';
+COMMENT ON COLUMN sj_job.task_type IS '浠诲姟绫诲瀷 1銆侀泦缇� 2銆佸箍鎾� 3銆佸垏鐗�';
+COMMENT ON COLUMN sj_job.route_key IS '璺敱绛栫暐';
+COMMENT ON COLUMN sj_job.executor_type IS '鎵ц鍣ㄧ被鍨�';
+COMMENT ON COLUMN sj_job.executor_info IS '鎵ц鍣ㄥ悕绉�';
+COMMENT ON COLUMN sj_job.trigger_type IS '瑙﹀彂绫诲瀷 1.CRON 琛ㄨ揪寮� 2. 鍥哄畾鏃堕棿';
+COMMENT ON COLUMN sj_job.trigger_interval IS '闂撮殧鏃堕暱';
+COMMENT ON COLUMN sj_job.block_strategy IS '闃诲绛栫暐 1銆佷涪寮� 2銆佽鐩� 3銆佸苟琛�';
+COMMENT ON COLUMN sj_job.executor_timeout IS '浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇';
+COMMENT ON COLUMN sj_job.max_retry_times IS '鏈�澶ч噸璇曟鏁�';
+COMMENT ON COLUMN sj_job.parallel_num IS '骞惰鏁�';
+COMMENT ON COLUMN sj_job.retry_interval IS '閲嶈瘯闂撮殧 ( s ) ';
+COMMENT ON COLUMN sj_job.bucket_index IS 'bucket';
+COMMENT ON COLUMN sj_job.resident IS '鏄惁鏄父椹讳换鍔�';
+COMMENT ON COLUMN sj_job.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_job.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_job.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_job.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_job.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_job IS '浠诲姟淇℃伅';
+
+INSERT INTO sj_job(namespace_id, group_name, job_name, args_str, args_type, next_trigger_at, job_status, task_type, route_key, executor_type, executor_info, trigger_type, trigger_interval, block_strategy,executor_timeout, max_retry_times, parallel_num, retry_interval, bucket_index, resident, description, ext_attrs, deleted, create_dt, update_dt) VALUES ('dev', 'ruoyi_group', 'demo-job', NULL, 1, 1710344035622, 1, 1, 4, 1, 'testJobExecutor', 2, '60', 1, 60, 3, 1, 1, 116, 0, '', '', 0, sysdate, sysdate);
+
+-- sj_job_log_message
+CREATE TABLE sj_job_log_message
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) NULL,
+ job_id number NOT NULL,
+ task_batch_id number NOT NULL,
+ task_id number NOT NULL,
+ message clob NULL,
+ log_num number DEFAULT 1 NOT NULL,
+ real_time number DEFAULT 0 NOT NULL,
+ ext_attrs varchar2(256) DEFAULT '' NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_job_log_message
+ ADD CONSTRAINT pk_sj_job_log_message PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_job_log_message_01 ON sj_job_log_message (task_batch_id, task_id);
+CREATE INDEX idx_sj_job_log_message_02 ON sj_job_log_message (create_dt);
+CREATE INDEX idx_sj_job_log_message_03 ON sj_job_log_message (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_job_log_message.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job_log_message.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job_log_message.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job_log_message.job_id IS '浠诲姟淇℃伅id';
+COMMENT ON COLUMN sj_job_log_message.task_batch_id IS '浠诲姟鎵规id';
+COMMENT ON COLUMN sj_job_log_message.task_id IS '璋冨害浠诲姟id';
+COMMENT ON COLUMN sj_job_log_message.message IS '璋冨害淇℃伅';
+COMMENT ON COLUMN sj_job_log_message.log_num IS '鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_log_message.real_time IS '涓婃姤鏃堕棿';
+COMMENT ON COLUMN sj_job_log_message.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_job_log_message.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON TABLE sj_job_log_message IS '璋冨害鏃ュ織';
+
+-- sj_job_task
+CREATE TABLE sj_job_task
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) NULL,
+ job_id number NOT NULL,
+ task_batch_id number NOT NULL,
+ parent_id number DEFAULT 0 NOT NULL,
+ task_status smallint DEFAULT 0 NOT NULL,
+ retry_count number DEFAULT 0 NOT NULL,
+ client_info varchar2(128) DEFAULT NULL NULL,
+ result_message clob NULL,
+ args_str clob DEFAULT NULL NULL,
+ args_type smallint DEFAULT 1 NOT NULL,
+ ext_attrs varchar2(256) DEFAULT '' NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_job_task
+ ADD CONSTRAINT pk_sj_job_task PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_job_task_01 ON sj_job_task (task_batch_id, task_status);
+CREATE INDEX idx_sj_job_task_02 ON sj_job_task (create_dt);
+CREATE INDEX idx_sj_job_task_03 ON sj_job_task (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_job_task.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job_task.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job_task.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job_task.job_id IS '浠诲姟淇℃伅id';
+COMMENT ON COLUMN sj_job_task.task_batch_id IS '璋冨害浠诲姟id';
+COMMENT ON COLUMN sj_job_task.parent_id IS '鐖舵墽琛屽櫒id';
+COMMENT ON COLUMN sj_job_task.task_status IS '鎵ц鐨勭姸鎬� 0銆佸け璐� 1銆佹垚鍔�';
+COMMENT ON COLUMN sj_job_task.retry_count IS '閲嶈瘯娆℃暟';
+COMMENT ON COLUMN sj_job_task.client_info IS '瀹㈡埛绔湴鍧� clientId#ip:port';
+COMMENT ON COLUMN sj_job_task.result_message IS '鎵ц缁撴灉';
+COMMENT ON COLUMN sj_job_task.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_job_task.args_type IS '鍙傛暟绫诲瀷 ';
+COMMENT ON COLUMN sj_job_task.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_job_task.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_job_task.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_job_task IS '浠诲姟瀹炰緥';
+
+-- sj_job_task_batch
+CREATE TABLE sj_job_task_batch
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) NULL,
+ job_id number NOT NULL,
+ workflow_node_id number DEFAULT 0 NOT NULL,
+ parent_workflow_node_id number DEFAULT 0 NOT NULL,
+ workflow_task_batch_id number DEFAULT 0 NOT NULL,
+ task_batch_status smallint DEFAULT 0 NOT NULL,
+ operation_reason smallint DEFAULT 0 NOT NULL,
+ execution_at number DEFAULT 0 NOT NULL,
+ system_task_type smallint DEFAULT 3 NOT NULL,
+ parent_id varchar2(64) DEFAULT '' NULL,
+ ext_attrs varchar2(256) DEFAULT '' NULL,
+ deleted smallint DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_job_task_batch
+ ADD CONSTRAINT pk_sj_job_task_batch PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_job_task_batch_01 ON sj_job_task_batch (job_id, task_batch_status);
+CREATE INDEX idx_sj_job_task_batch_02 ON sj_job_task_batch (create_dt);
+CREATE INDEX idx_sj_job_task_batch_03 ON sj_job_task_batch (namespace_id, group_name);
+CREATE INDEX idx_sj_job_task_batch_04 ON sj_job_task_batch (workflow_task_batch_id, workflow_node_id);
+
+COMMENT ON COLUMN sj_job_task_batch.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job_task_batch.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job_task_batch.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job_task_batch.job_id IS '浠诲姟id';
+COMMENT ON COLUMN sj_job_task_batch.workflow_node_id IS '宸ヤ綔娴佽妭鐐筰d';
+COMMENT ON COLUMN sj_job_task_batch.parent_workflow_node_id IS '宸ヤ綔娴佷换鍔$埗鎵规id';
+COMMENT ON COLUMN sj_job_task_batch.workflow_task_batch_id IS '宸ヤ綔娴佷换鍔℃壒娆d';
+COMMENT ON COLUMN sj_job_task_batch.task_batch_status IS '浠诲姟鎵规鐘舵�� 0銆佸け璐� 1銆佹垚鍔�';
+COMMENT ON COLUMN sj_job_task_batch.operation_reason IS '鎿嶄綔鍘熷洜';
+COMMENT ON COLUMN sj_job_task_batch.execution_at IS '浠诲姟鎵ц鏃堕棿';
+COMMENT ON COLUMN sj_job_task_batch.system_task_type IS '浠诲姟绫诲瀷 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟';
+COMMENT ON COLUMN sj_job_task_batch.parent_id IS '鐖惰妭鐐�';
+COMMENT ON COLUMN sj_job_task_batch.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_job_task_batch.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_job_task_batch.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_job_task_batch.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_job_task_batch IS '浠诲姟鎵规';
+
+-- sj_job_summary
+CREATE TABLE sj_job_summary
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) DEFAULT '' NULL,
+ business_id number NOT NULL,
+ system_task_type smallint DEFAULT 3 NOT NULL,
+ trigger_at date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ success_num number DEFAULT 0 NOT NULL,
+ fail_num number DEFAULT 0 NOT NULL,
+ fail_reason varchar2(512) DEFAULT '' NULL,
+ stop_num number DEFAULT 0 NOT NULL,
+ stop_reason varchar2(512) DEFAULT '' NULL,
+ cancel_num number DEFAULT 0 NOT NULL,
+ cancel_reason varchar2(512) DEFAULT '' NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_job_summary
+ ADD CONSTRAINT pk_sj_job_summary PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX uk_sj_job_summary_01 ON sj_job_summary (trigger_at, system_task_type, business_id);
+
+CREATE INDEX idx_sj_job_summary_01 ON sj_job_summary (namespace_id, group_name, business_id);
+
+COMMENT ON COLUMN sj_job_summary.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job_summary.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job_summary.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job_summary.business_id IS '涓氬姟id ( job_id鎴杦orkflow_id ) ';
+COMMENT ON COLUMN sj_job_summary.system_task_type IS '浠诲姟绫诲瀷 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟';
+COMMENT ON COLUMN sj_job_summary.trigger_at IS '缁熻鏃堕棿';
+COMMENT ON COLUMN sj_job_summary.success_num IS '鎵ц鎴愬姛-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_summary.fail_num IS '鎵ц澶辫触-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_summary.fail_reason IS '澶辫触鍘熷洜';
+COMMENT ON COLUMN sj_job_summary.stop_num IS '鎵ц澶辫触-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_summary.stop_reason IS '澶辫触鍘熷洜';
+COMMENT ON COLUMN sj_job_summary.cancel_num IS '鎵ц澶辫触-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_summary.cancel_reason IS '澶辫触鍘熷洜';
+COMMENT ON COLUMN sj_job_summary.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_job_summary.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_job_summary IS 'DashBoard_Job';
+
+-- sj_retry_summary
+CREATE TABLE sj_retry_summary
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) DEFAULT '' NULL,
+ scene_name varchar2(50) DEFAULT '' NULL,
+ trigger_at date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ running_num number DEFAULT 0 NOT NULL,
+ finish_num number DEFAULT 0 NOT NULL,
+ max_count_num number DEFAULT 0 NOT NULL,
+ suspend_num number DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_retry_summary
+ ADD CONSTRAINT pk_sj_retry_summary PRIMARY KEY (id);
+
+CREATE UNIQUE INDEX uk_sj_retry_summary_01 ON sj_retry_summary (namespace_id, group_name, scene_name, trigger_at);
+
+CREATE INDEX idx_sj_retry_summary_01 ON sj_retry_summary (trigger_at);
+
+COMMENT ON COLUMN sj_retry_summary.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_summary.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_summary.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_summary.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_summary.trigger_at IS '缁熻鏃堕棿';
+COMMENT ON COLUMN sj_retry_summary.running_num IS '閲嶈瘯涓�-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_summary.finish_num IS '閲嶈瘯瀹屾垚-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_summary.max_count_num IS '閲嶈瘯鍒拌揪鏈�澶ф鏁�-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_summary.suspend_num IS '鏆傚仠閲嶈瘯-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_summary.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_retry_summary.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_retry_summary IS 'DashBoard_Retry';
+
+-- sj_workflow
+CREATE TABLE sj_workflow
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ workflow_name varchar2(64) NULL,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) NULL,
+ workflow_status smallint DEFAULT 1 NOT NULL,
+ trigger_type smallint NOT NULL,
+ trigger_interval varchar2(255) NULL,
+ next_trigger_at number NOT NULL,
+ block_strategy smallint DEFAULT 1 NOT NULL,
+ executor_timeout number DEFAULT 0 NOT NULL,
+ description varchar2(256) DEFAULT '' NULL,
+ flow_info clob DEFAULT NULL NULL,
+ bucket_index number DEFAULT 0 NOT NULL,
+ version number NOT NULL,
+ ext_attrs varchar2(256) DEFAULT '' NULL,
+ deleted smallint DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_workflow
+ ADD CONSTRAINT pk_sj_workflow PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_workflow_01 ON sj_workflow (create_dt);
+CREATE INDEX idx_sj_workflow_02 ON sj_workflow (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_workflow.id IS '涓婚敭';
+COMMENT ON COLUMN sj_workflow.workflow_name IS '宸ヤ綔娴佸悕绉�';
+COMMENT ON COLUMN sj_workflow.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_workflow.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_workflow.workflow_status IS '宸ヤ綔娴佺姸鎬� 0銆佸叧闂��1銆佸紑鍚�';
+COMMENT ON COLUMN sj_workflow.trigger_type IS '瑙﹀彂绫诲瀷 1.CRON 琛ㄨ揪寮� 2. 鍥哄畾鏃堕棿';
+COMMENT ON COLUMN sj_workflow.trigger_interval IS '闂撮殧鏃堕暱';
+COMMENT ON COLUMN sj_workflow.next_trigger_at IS '涓嬫瑙﹀彂鏃堕棿';
+COMMENT ON COLUMN sj_workflow.block_strategy IS '闃诲绛栫暐 1銆佷涪寮� 2銆佽鐩� 3銆佸苟琛�';
+COMMENT ON COLUMN sj_workflow.executor_timeout IS '浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇';
+COMMENT ON COLUMN sj_workflow.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_workflow.flow_info IS '娴佺▼淇℃伅';
+COMMENT ON COLUMN sj_workflow.bucket_index IS 'bucket';
+COMMENT ON COLUMN sj_workflow.version IS '鐗堟湰鍙�';
+COMMENT ON COLUMN sj_workflow.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_workflow.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_workflow.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_workflow.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_workflow IS '宸ヤ綔娴�';
+
+-- sj_workflow_node
+CREATE TABLE sj_workflow_node
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ node_name varchar2(64) NULL,
+ group_name varchar2(64) NULL,
+ job_id number NOT NULL,
+ workflow_id number NOT NULL,
+ node_type smallint DEFAULT 1 NOT NULL,
+ expression_type smallint DEFAULT 0 NOT NULL,
+ fail_strategy smallint DEFAULT 1 NOT NULL,
+ workflow_node_status smallint DEFAULT 1 NOT NULL,
+ priority_level number DEFAULT 1 NOT NULL,
+ node_info clob DEFAULT NULL NULL,
+ version number NOT NULL,
+ ext_attrs varchar2(256) DEFAULT '' NULL,
+ deleted smallint DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_workflow_node
+ ADD CONSTRAINT pk_sj_workflow_node PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_workflow_node_01 ON sj_workflow_node (create_dt);
+CREATE INDEX idx_sj_workflow_node_02 ON sj_workflow_node (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_workflow_node.id IS '涓婚敭';
+COMMENT ON COLUMN sj_workflow_node.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_workflow_node.node_name IS '鑺傜偣鍚嶇О';
+COMMENT ON COLUMN sj_workflow_node.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_workflow_node.job_id IS '浠诲姟淇℃伅id';
+COMMENT ON COLUMN sj_workflow_node.workflow_id IS '宸ヤ綔娴両D';
+COMMENT ON COLUMN sj_workflow_node.node_type IS '1銆佷换鍔¤妭鐐� 2銆佹潯浠惰妭鐐�';
+COMMENT ON COLUMN sj_workflow_node.expression_type IS '1銆丼pEl銆�2銆丄viator 3銆丵L';
+COMMENT ON COLUMN sj_workflow_node.fail_strategy IS '澶辫触绛栫暐 1銆佽烦杩� 2銆侀樆濉�';
+COMMENT ON COLUMN sj_workflow_node.workflow_node_status IS '宸ヤ綔娴佽妭鐐圭姸鎬� 0銆佸叧闂��1銆佸紑鍚�';
+COMMENT ON COLUMN sj_workflow_node.priority_level IS '浼樺厛绾�';
+COMMENT ON COLUMN sj_workflow_node.node_info IS '鑺傜偣淇℃伅 ';
+COMMENT ON COLUMN sj_workflow_node.version IS '鐗堟湰鍙�';
+COMMENT ON COLUMN sj_workflow_node.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_workflow_node.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_workflow_node.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_workflow_node.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_workflow_node IS '宸ヤ綔娴佽妭鐐�';
+
+-- sj_workflow_task_batch
+CREATE TABLE sj_workflow_task_batch
+(
+ id number GENERATED ALWAYS AS IDENTITY,
+ namespace_id varchar2(64) DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' NULL,
+ group_name varchar2(64) NULL,
+ workflow_id number NOT NULL,
+ task_batch_status smallint DEFAULT 0 NOT NULL,
+ operation_reason smallint DEFAULT 0 NOT NULL,
+ flow_info clob DEFAULT NULL NULL,
+ execution_at number DEFAULT 0 NOT NULL,
+ ext_attrs varchar2(256) DEFAULT '' NULL,
+ deleted smallint DEFAULT 0 NOT NULL,
+ create_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL,
+ update_dt date DEFAULT CURRENT_TIMESTAMP NOT NULL
+);
+
+ALTER TABLE sj_workflow_task_batch
+ ADD CONSTRAINT pk_sj_workflow_task_batch PRIMARY KEY (id);
+
+CREATE INDEX idx_sj_workflow_task_batch_01 ON sj_workflow_task_batch (workflow_id, task_batch_status);
+CREATE INDEX idx_sj_workflow_task_batch_02 ON sj_workflow_task_batch (create_dt);
+CREATE INDEX idx_sj_workflow_task_batch_03 ON sj_workflow_task_batch (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_workflow_task_batch.id IS '涓婚敭';
+COMMENT ON COLUMN sj_workflow_task_batch.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_workflow_task_batch.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_workflow_task_batch.workflow_id IS '宸ヤ綔娴佷换鍔d';
+COMMENT ON COLUMN sj_workflow_task_batch.task_batch_status IS '浠诲姟鎵规鐘舵�� 0銆佸け璐� 1銆佹垚鍔�';
+COMMENT ON COLUMN sj_workflow_task_batch.operation_reason IS '鎿嶄綔鍘熷洜';
+COMMENT ON COLUMN sj_workflow_task_batch.flow_info IS '娴佺▼淇℃伅';
+COMMENT ON COLUMN sj_workflow_task_batch.execution_at IS '浠诲姟鎵ц鏃堕棿';
+COMMENT ON COLUMN sj_workflow_task_batch.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_workflow_task_batch.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_workflow_task_batch.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_workflow_task_batch.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_workflow_task_batch IS '宸ヤ綔娴佹壒娆�';
+
diff --git a/script/sql/postgres/flowable.sql b/script/sql/postgres/flowable.sql
new file mode 100644
index 0000000..eff4eeb
--- /dev/null
+++ b/script/sql/postgres/flowable.sql
@@ -0,0 +1,341 @@
+insert into sys_menu values('11616', '宸ヤ綔娴�' , '0', '6', 'workflow', '', '', '1', '0', 'M', '0', '0', '', 'workflow', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11617', '妯″瀷绠$悊', '11616', '2', 'model', 'workflow/model/index', '', '1', '1', 'C', '0', '0', 'workflow:model:list', 'model', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11618', '鎴戠殑浠诲姟', '0', '7', 'task', '', '', '1', '0', 'M', '0', '0', '', 'my-task', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11619', '鎴戠殑寰呭姙', '11618', '2', 'taskWaiting', 'workflow/task/taskWaiting', '', '1', '1', 'C', '0', '0', '', 'waiting', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11632', '鎴戠殑宸插姙', '11618', '3', 'taskFinish', 'workflow/task/taskFinish', '', '1', '1', 'C', '0', '0', '', 'finish', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11633', '鎴戠殑鎶勯��', '11618', '4', 'taskCopyList', 'workflow/task/taskCopyList', '', '1', '1', 'C', '0', '0', '', 'my-copy', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11620', '娴佺▼瀹氫箟', '11616', '3', 'processDefinition', 'workflow/processDefinition/index', '', '1', '1', 'C', '0', '0', '', 'process-definition', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11621', '娴佺▼瀹炰緥', '11630', '1', 'processInstance', 'workflow/processInstance/index', '', '1', '1', 'C', '0', '0', '', 'tree-table', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11622', '娴佺▼鍒嗙被', '11616', '1', 'category', 'workflow/category/index', '', '1', '0', 'C', '0', '0', 'workflow:category:list', 'category', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11629', '鎴戝彂璧风殑', '11618', '1', 'myDocument', 'workflow/task/myDocument', '', '1', '1', 'C', '0', '0', '', 'guide', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11630', '娴佺▼鐩戞帶', '11616', '4', 'monitor', '', '', '1', '0', 'M', '0', '0', '', 'monitor', 103, 1, now(), NULL, NULL, '');
+insert into sys_menu values('11631', '寰呭姙浠诲姟', '11630', '2', 'allTaskWaiting', 'workflow/task/allTaskWaiting', '', '1', '1', 'C', '0', '0', '', 'waiting', 103, 1, now(), NULL, NULL, '');
+
+
+-- 娴佺▼鍒嗙被绠$悊鐩稿叧鎸夐挳
+insert into sys_menu values ('11623', '娴佺▼鍒嗙被鏌ヨ', '11622', '1', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:query', '#', 103, 1, now(), null, null, '');
+insert into sys_menu values ('11624', '娴佺▼鍒嗙被鏂板', '11622', '2', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:add', '#', 103, 1, now(), null, null, '');
+insert into sys_menu values ('11625', '娴佺▼鍒嗙被淇敼', '11622', '3', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:edit', '#', 103, 1, now(), null, null, '');
+insert into sys_menu values ('11626', '娴佺▼鍒嗙被鍒犻櫎', '11622', '4', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:remove','#', 103, 1, now(), null, null, '');
+insert into sys_menu values ('11627', '娴佺▼鍒嗙被瀵煎嚭', '11622', '5', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:export','#', 103, 1, now(), null, null, '');
+-- 璇峰亣鍗曚俊鎭�
+create table test_leave
+(
+ id bigint not null
+ constraint test_leave_pk
+ primary key,
+ leave_type varchar(255),
+ start_date timestamp,
+ end_date timestamp,
+ leave_days bigint,
+ remark varchar(255),
+ create_dept bigint,
+ create_by bigint,
+ create_time timestamp,
+ update_by bigint,
+ update_time timestamp,
+ tenant_id varchar(20)
+);
+
+comment on table test_leave is '璇峰亣鐢宠琛�';
+
+comment on column test_leave.id is '涓婚敭';
+
+comment on column test_leave.leave_type is '璇峰亣绫诲瀷';
+
+comment on column test_leave.start_date is '寮�濮嬫椂闂�';
+
+comment on column test_leave.end_date is '缁撴潫鏃堕棿';
+
+comment on column test_leave.remark is '璇峰亣鍘熷洜';
+
+comment on column test_leave.create_dept is '鍒涘缓閮ㄩ棬';
+
+comment on column test_leave.create_by is '鍒涘缓鑰�';
+
+comment on column test_leave.create_time is '鍒涘缓鏃堕棿';
+
+comment on column test_leave.update_by is '鏇存柊鑰�';
+
+comment on column test_leave.update_time is '鏇存柊鏃堕棿';
+
+comment on column test_leave.tenant_id is '绉熸埛缂栫爜';
+
+alter table test_leave
+ owner to postgres;
+
+-- 娴佺▼鍒嗙被淇℃伅琛�
+create table wf_category
+(
+ id bigint not null
+ constraint wf_category_pk
+ primary key,
+ category_name varchar(255),
+ category_code varchar(255),
+ parent_id bigint,
+ sort_num bigint,
+ tenant_id varchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time timestamp,
+ update_by bigint,
+ update_time timestamp
+);
+
+comment on table wf_category is '娴佺▼鍒嗙被';
+
+comment on column wf_category.id is '涓婚敭';
+
+comment on column wf_category.category_name is '鍒嗙被鍚嶇О';
+
+comment on column wf_category.category_code is '鍒嗙被缂栫爜';
+
+comment on column wf_category.parent_id is '鐖剁骇id';
+
+comment on column wf_category.sort_num is '鎺掑簭';
+
+comment on column wf_category.tenant_id is '绉熸埛id';
+
+comment on column wf_category.create_dept is '鍒涘缓閮ㄩ棬';
+
+comment on column wf_category.create_by is '鍒涘缓鑰�';
+
+comment on column wf_category.create_time is '鍒涘缓鏃堕棿';
+
+comment on column wf_category.update_by is '淇敼鑰�';
+
+comment on column wf_category.update_time is '淇敼鏃堕棿';
+
+alter table wf_category
+ owner to postgres;
+
+create unique index uni_category_code
+ on wf_category (category_code);
+
+INSERT INTO wf_category values (1, 'OA', 'OA', 0, 0, '000000', 103, 1, now(), 1, now());
+
+create table wf_task_back_node
+(
+ id bigint not null
+ constraint pk_wf_task_back_node
+ primary key,
+ node_id varchar(255) not null,
+ node_name varchar(255) not null,
+ order_no bigint not null,
+ instance_id varchar(255) not null,
+ task_type varchar(255) not null,
+ assignee varchar(2000) not null,
+ tenant_id varchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time timestamp,
+ update_by bigint,
+ update_time timestamp
+);
+
+comment on table wf_task_back_node is '鑺傜偣瀹℃壒璁板綍';
+
+comment on column wf_task_back_node.id is '涓婚敭';
+
+comment on column wf_task_back_node.node_id is '鑺傜偣id';
+
+comment on column wf_task_back_node.node_name is '鑺傜偣鍚嶇О';
+
+comment on column wf_task_back_node.order_no is '鎺掑簭';
+
+comment on column wf_task_back_node.instance_id is '娴佺▼瀹炰緥id';
+
+comment on column wf_task_back_node.task_type is '鑺傜偣绫诲瀷';
+
+comment on column wf_task_back_node.assignee is '瀹℃壒浜�';
+
+comment on column wf_task_back_node.tenant_id is '绉熸埛id';
+
+comment on column wf_task_back_node.create_dept is '鍒涘缓閮ㄩ棬';
+
+comment on column wf_task_back_node.create_by is '鍒涘缓鑰�';
+
+comment on column wf_task_back_node.create_time is '鍒涘缓鏃堕棿';
+
+comment on column wf_task_back_node.update_by is '淇敼鑰�';
+
+comment on column wf_task_back_node.update_time is '淇敼鏃堕棿';
+
+alter table wf_task_back_node
+ owner to postgres;
+
+create table wf_definition_config
+(
+ id bigint not null
+ constraint pk_wf_definition_config
+ primary key,
+ table_name varchar(255) not null,
+ definition_id varchar(255) not null,
+ process_key varchar(255) not null,
+ version bigint not null,
+ tenant_id varchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time timestamp,
+ update_by bigint,
+ update_time timestamp
+);
+
+comment on table wf_definition_config is '娴佺▼瀹氫箟閰嶇疆';
+
+comment on column wf_definition_config.id is '涓婚敭';
+
+comment on column wf_definition_config.table_name is '琛ㄥ悕';
+
+comment on column wf_definition_config.definition_id is '娴佺▼瀹氫箟ID';
+
+comment on column wf_definition_config.process_key is '娴佺▼KEY';
+
+comment on column wf_definition_config.version is '娴佺▼鐗堟湰';
+
+comment on column wf_definition_config.tenant_id is '绉熸埛id';
+
+comment on column wf_definition_config.create_dept is '鍒涘缓閮ㄩ棬';
+
+comment on column wf_definition_config.create_by is '鍒涘缓鑰�';
+
+comment on column wf_definition_config.create_time is '鍒涘缓鏃堕棿';
+
+comment on column wf_definition_config.update_by is '淇敼鑰�';
+
+comment on column wf_definition_config.update_time is '淇敼鏃堕棿';
+
+alter table wf_definition_config
+ owner to postgres;
+create unique index uni_definition_id
+ on wf_definition_config (definition_id);
+
+create table wf_form_manage
+(
+ id bigint not null
+ constraint pk_wf_form_manage
+ primary key,
+ form_name varchar(255) not null,
+ form_type varchar(255) not null,
+ router varchar(255) not null,
+ remark varchar(500),
+ tenant_id varchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time timestamp,
+ update_by bigint,
+ update_time timestamp
+);
+
+comment on table wf_form_manage is '琛ㄥ崟绠$悊';
+
+comment on column wf_form_manage.id is '涓婚敭';
+
+comment on column wf_form_manage.form_name is '琛ㄥ崟鍚嶇О';
+
+comment on column wf_form_manage.form_type is '琛ㄥ崟绫诲瀷';
+
+comment on column wf_form_manage.router is '璺敱鍦板潃/琛ㄥ崟ID';
+
+comment on column wf_form_manage.remark is '澶囨敞';
+
+comment on column wf_form_manage.tenant_id is '绉熸埛id';
+
+comment on column wf_form_manage.create_dept is '鍒涘缓閮ㄩ棬';
+
+comment on column wf_form_manage.create_by is '鍒涘缓鑰�';
+
+comment on column wf_form_manage.create_time is '鍒涘缓鏃堕棿';
+
+comment on column wf_form_manage.update_by is '淇敼鑰�';
+
+comment on column wf_form_manage.update_time is '淇敼鏃堕棿';
+
+insert into wf_form_manage(id, form_name, form_type, router, remark, tenant_id, create_dept, create_by, create_time, update_by, update_time) VALUES (1, '璇峰亣鐢宠', 'static', '/demo/leaveEdit/index', NULL, '000000', 103, 1, now(), 1, now());
+
+create table wf_node_config
+(
+ id bigint not null
+ constraint pk_wf_node_config
+ primary key,
+ form_id bigint,
+ form_type varchar(255),
+ node_name varchar(255) not null,
+ node_id varchar(255) not null,
+ definition_id varchar(255) not null,
+ apply_user_task char(1) default '0',
+ tenant_id varchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time timestamp,
+ update_by bigint,
+ update_time timestamp
+);
+
+comment on table wf_node_config is '鑺傜偣閰嶇疆';
+
+comment on column wf_node_config.id is '涓婚敭';
+
+comment on column wf_node_config.form_id is '琛ㄥ崟id';
+
+comment on column wf_node_config.form_type is '琛ㄥ崟绫诲瀷';
+
+comment on column wf_node_config.node_id is '鑺傜偣id';
+
+comment on column wf_node_config.node_name is '鑺傜偣鍚嶇О';
+
+comment on column wf_node_config.definition_id is '娴佺▼瀹氫箟id';
+
+comment on column wf_node_config.apply_user_task is '鏄惁涓虹敵璇蜂汉鑺傜偣 锛�0鏄� 1鍚︼級';
+
+comment on column wf_node_config.tenant_id is '绉熸埛id';
+
+comment on column wf_node_config.create_dept is '鍒涘缓閮ㄩ棬';
+
+comment on column wf_node_config.create_by is '鍒涘缓鑰�';
+
+comment on column wf_node_config.create_time is '鍒涘缓鏃堕棿';
+
+comment on column wf_node_config.update_by is '淇敼鑰�';
+
+comment on column wf_node_config.update_time is '淇敼鏃堕棿';
+
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11638, '璇峰亣鐢宠', 5, 1, 'leave', 'workflow/leave/index', 1, 0, 'C', '0', '0', 'demo:leave:list', '#', 103, 1, now(), NULL, NULL, '璇峰亣鐢宠鑿滃崟');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11639, '璇峰亣鐢宠鏌ヨ', 11638, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:query', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11640, '璇峰亣鐢宠鏂板', 11638, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:add', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11641, '璇峰亣鐢宠淇敼', 11638, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:edit', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11642, '璇峰亣鐢宠鍒犻櫎', 11638, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:remove', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11643, '璇峰亣鐢宠瀵煎嚭', 11638, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:export', '#', 103, 1, now(), NULL, NULL, '');
+
+INSERT INTO sys_dict_type(dict_id, tenant_id, dict_name, dict_type, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (13, '000000', '涓氬姟鐘舵��', 'wf_business_status', 103, 1, now(), NULL, NULL, '涓氬姟鐘舵�佸垪琛�');
+INSERT INTO sys_dict_type(dict_id, tenant_id, dict_name, dict_type, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (14, '000000', '琛ㄥ崟绫诲瀷', 'wf_form_type', 103, 1, now(), NULL, NULL, '琛ㄥ崟绫诲瀷鍒楄〃');
+
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (39, '000000', 1, '宸叉挙閿�', 'cancel', 'wf_business_status', '', 'danger', 'N', 103, 1, now(), NULL, NULL, '宸叉挙閿�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (40, '000000', 2, '鑽夌', 'draft', 'wf_business_status', '', 'info', 'N', 103, 1, now(), NULL, NULL, '鑽夌');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (41, '000000', 3, '寰呭鏍�', 'waiting', 'wf_business_status', '', 'primary', 'N', 103, 1,now(), NULL, NULL, '寰呭鏍�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (42, '000000', 4, '宸插畬鎴�', 'finish', 'wf_business_status', '', 'success', 'N', 103, 1, now(), NULL, NULL, '宸插畬鎴�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (43, '000000', 5, '宸蹭綔搴�', 'invalid', 'wf_business_status', '', 'danger', 'N', 103, 1, now(), NULL, NULL, '宸蹭綔搴�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (44, '000000', 6, '宸查��鍥�', 'back', 'wf_business_status', '', 'danger', 'N', 103, 1, now(), NULL, NULL, '宸查��鍥�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (45, '000000', 7, '宸茬粓姝�', 'termination', 'wf_business_status', '', 'danger', 'N', 103, 1,now(), NULL, NULL, '宸茬粓姝�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (46, '000000', 1, '鑷畾涔夎〃鍗�', 'static', 'wf_form_type', '', 'success', 'N', 103, 1, now(), NULL, NULL, '鑷畾涔夎〃鍗�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (47, '000000', 2, '鍔ㄦ�佽〃鍗�', 'dynamic', 'wf_form_type', '', 'primary', 'N', 103, 1, now(), NULL, NULL, '鍔ㄦ�佽〃鍗�');
+
+-- 琛ㄥ崟绠$悊 SQL
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11628, '琛ㄥ崟绠$悊', '11616', '5', 'formManage', 'workflow/formManage/index', 1, 0, 'C', '0', '0', 'workflow:formManage:list', 'tree-table', 103, 1, now(), null, null, '琛ㄥ崟绠$悊鑿滃崟');
+
+-- 琛ㄥ崟绠$悊鎸夐挳 SQL
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11644, '琛ㄥ崟绠$悊鏌ヨ', 11628, '1', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:query', '', 103, 1, now(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11645, '琛ㄥ崟绠$悊鏂板', 11628, '2', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:add', '', 103, 1, now(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11646, '琛ㄥ崟绠$悊淇敼', 11628, '3', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:edit', '', 103, 1, now(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11647, '琛ㄥ崟绠$悊鍒犻櫎', 11628, '4', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:remove', '', 103, 1, now(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11648, '琛ㄥ崟绠$悊瀵煎嚭', 11628, '5', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:export', 'tree-table', 103, 1, now(), null, null, '');
diff --git a/script/sql/postgres/postgres_ry_vue_5.X.sql b/script/sql/postgres/postgres_ry_vue_5.X.sql
index a6d6f1a..9b2169e 100644
--- a/script/sql/postgres/postgres_ry_vue_5.X.sql
+++ b/script/sql/postgres/postgres_ry_vue_5.X.sql
@@ -20,7 +20,7 @@
union_id varchar(255) default null::varchar,
scope varchar(255) default null::varchar,
token_type varchar(255) default null::varchar,
- id_token varchar(255) default null::varchar,
+ id_token varchar(2000) default null::varchar,
mac_algorithm varchar(255) default null::varchar,
mac_key varchar(255) default null::varchar,
code varchar(255) default null::varchar,
@@ -69,7 +69,6 @@
-- ----------------------------
-- 绉熸埛琛�
-- ----------------------------
-drop table if exists sys_tenant;
create table if not exists sys_tenant
(
id int8,
@@ -128,7 +127,6 @@
-- ----------------------------
-- 绉熸埛濂楅琛�
-- ----------------------------
-drop table if exists sys_tenant_package;
create table if not exists sys_tenant_package
(
package_id int8,
@@ -164,7 +162,6 @@
-- ----------------------------
-- 1銆侀儴闂ㄨ〃
-- ----------------------------
-drop table if exists sys_dept;
create table if not exists sys_dept
(
dept_id int8,
@@ -172,6 +169,7 @@
parent_id int8 default 0,
ancestors varchar(500)default ''::varchar,
dept_name varchar(30) default ''::varchar,
+ dept_category varchar(100) default null::varchar,
order_num int4 default 0,
leader int8 default null,
phone varchar(11) default null::varchar,
@@ -192,6 +190,7 @@
comment on column sys_dept.parent_id is '鐖堕儴闂↖D';
comment on column sys_dept.ancestors is '绁栫骇鍒楄〃';
comment on column sys_dept.dept_name is '閮ㄩ棬鍚嶇О';
+comment on column sys_dept.dept_category is '閮ㄩ棬绫诲埆缂栫爜';
comment on column sys_dept.order_num is '鏄剧ず椤哄簭';
comment on column sys_dept.leader is '璐熻矗浜�';
comment on column sys_dept.phone is '鑱旂郴鐢佃瘽';
@@ -207,21 +206,20 @@
-- ----------------------------
-- 鍒濆鍖�-閮ㄩ棬琛ㄦ暟鎹�
-- ----------------------------
-insert into sys_dept values(100, '000000', 0, '0', 'XXX绉戞妧', 0, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-insert into sys_dept values(101, '000000', 100, '0,100', '娣卞湷鎬诲叕鍙�', 1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-insert into sys_dept values(102, '000000', 100, '0,100', '闀挎矙鍒嗗叕鍙�', 2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-insert into sys_dept values(103, '000000', 101, '0,100,101', '鐮斿彂閮ㄩ棬', 1, 1, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-insert into sys_dept values(104, '000000', 101, '0,100,101', '甯傚満閮ㄩ棬', 2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-insert into sys_dept values(105, '000000', 101, '0,100,101', '娴嬭瘯閮ㄩ棬', 3, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-insert into sys_dept values(106, '000000', 101, '0,100,101', '璐㈠姟閮ㄩ棬', 4, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-insert into sys_dept values(107, '000000', 101, '0,100,101', '杩愮淮閮ㄩ棬', 5, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-insert into sys_dept values(108, '000000', 102, '0,100,102', '甯傚満閮ㄩ棬', 1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-insert into sys_dept values(109, '000000', 102, '0,100,102', '璐㈠姟閮ㄩ棬', 2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(100, '000000', 0, '0', 'XXX绉戞妧', null,0, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(101, '000000', 100, '0,100', '娣卞湷鎬诲叕鍙�', null,1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(102, '000000', 100, '0,100', '闀挎矙鍒嗗叕鍙�', null,2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(103, '000000', 101, '0,100,101', '鐮斿彂閮ㄩ棬', null,1, 1, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(104, '000000', 101, '0,100,101', '甯傚満閮ㄩ棬', null,2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(105, '000000', 101, '0,100,101', '娴嬭瘯閮ㄩ棬', null,3, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(106, '000000', 101, '0,100,101', '璐㈠姟閮ㄩ棬', null,4, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(107, '000000', 101, '0,100,101', '杩愮淮閮ㄩ棬', null,5, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(108, '000000', 102, '0,100,102', '甯傚満閮ㄩ棬', null,1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
+insert into sys_dept values(109, '000000', 102, '0,100,102', '璐㈠姟閮ㄩ棬', null,2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, now(), null, null);
-- ----------------------------
-- 2銆佺敤鎴蜂俊鎭〃
-- ----------------------------
-drop table if exists sys_user;
create table if not exists sys_user
(
user_id int8,
@@ -276,18 +274,19 @@
-- 鍒濆鍖�-鐢ㄦ埛淇℃伅琛ㄦ暟鎹�
-- ----------------------------
insert into sys_user values(1, '000000', 103, 'admin', '鐤媯鐨勭嫯瀛怢i', 'sys_user', 'crazyLionLi@163.com', '15888888888', '1', null, '$2a$10$7JB720yubVSZvUI0rEqK/.VqGOZTH.ulu33dHOiBE8ByOhJIrdAu2', '0', '0', '127.0.0.1', now(), 103, 1, now(), null, null, '绠$悊鍛�');
-insert into sys_user values(2, '000000', 105, 'lionli', '鐤媯鐨勭嫯瀛怢i', 'sys_user', 'crazyLionLi@qq.com', '15666666666', '1', null, '$2a$10$7JB720yubVSZvUI0rEqK/.VqGOZTH.ulu33dHOiBE8ByOhJIrdAu2', '0', '0', '127.0.0.1', now(), 103, 1, now(), null, null, '娴嬭瘯鍛�');
-
+insert into sys_user VALUES(3, '000000', 108, 'test', '鏈儴闂ㄥ強浠ヤ笅 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', now(), 103, 1, now(), 3, now(), NULL);
+insert into sys_user VALUES(4, '000000', 102, 'test1', '浠呮湰浜� 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', now(), 103, 1, now(), 4, now(), NULL);
-- ----------------------------
-- 3銆佸矖浣嶄俊鎭〃
-- ----------------------------
-drop table if exists sys_post;
create table if not exists sys_post
(
post_id int8,
tenant_id varchar(20) default '000000'::varchar,
+ dept_id int8,
post_code varchar(64) not null,
+ post_category varchar(100) default null,
post_name varchar(50) not null,
post_sort int4 not null,
status char not null,
@@ -303,7 +302,9 @@
comment on table sys_post is '宀椾綅淇℃伅琛�';
comment on column sys_post.post_id is '宀椾綅ID';
comment on column sys_post.tenant_id is '绉熸埛缂栧彿';
+comment on column sys_post.dept_id is '閮ㄩ棬id';
comment on column sys_post.post_code is '宀椾綅缂栫爜';
+comment on column sys_post.post_category is '宀椾綅绫诲埆缂栫爜';
comment on column sys_post.post_name is '宀椾綅鍚嶇О';
comment on column sys_post.post_sort is '鏄剧ず椤哄簭';
comment on column sys_post.status is '鐘舵�侊紙0姝e父 1鍋滅敤锛�';
@@ -317,15 +318,14 @@
-- ----------------------------
-- 鍒濆鍖�-宀椾綅淇℃伅琛ㄦ暟鎹�
-- ----------------------------
-insert into sys_post values(1, '000000', 'ceo', '钁d簨闀�', 1, '0', 103, 1, now(), null, null, '');
-insert into sys_post values(2, '000000', 'se', '椤圭洰缁忕悊', 2, '0', 103, 1, now(), null, null, '');
-insert into sys_post values(3, '000000', 'hr', '浜哄姏璧勬簮', 3, '0', 103, 1, now(), null, null, '');
-insert into sys_post values(4, '000000', 'user', '鏅�氬憳宸�', 4, '0', 103, 1, now(), null, null, '');
+insert into sys_post values(1, '000000', 103, 'ceo', null, '钁d簨闀�', 1, '0', 103, 1, now(), null, null, '');
+insert into sys_post values(2, '000000', 100, 'se', null, '椤圭洰缁忕悊', 2, '0', 103, 1, now(), null, null, '');
+insert into sys_post values(3, '000000', 100, 'hr', null, '浜哄姏璧勬簮', 3, '0', 103, 1, now(), null, null, '');
+insert into sys_post values(4, '000000', 100, 'user', null, '鏅�氬憳宸�', 4, '0', 103, 1, now(), null, null, '');
-- ----------------------------
-- 4銆佽鑹蹭俊鎭〃
-- ----------------------------
-drop table if exists sys_role;
create table if not exists sys_role
(
role_id int8,
@@ -369,13 +369,12 @@
-- 鍒濆鍖�-瑙掕壊淇℃伅琛ㄦ暟鎹�
-- ----------------------------
insert into sys_role values('1', '000000', '瓒呯骇绠$悊鍛�', 'superadmin', 1, '1', 't', 't', '0', '0', 103, 1, now(), null, null, '瓒呯骇绠$悊鍛�');
-insert into sys_role values('2', '000000', '鏅�氳鑹�', 'common', 2, '2', 't', 't', '0', '0', 103, 1, now(), null, null, '鏅�氳鑹�');
-
+insert into sys_role values('3', '000000', '鏈儴闂ㄥ強浠ヤ笅', 'test1', 3, '4', 't', 't', '0', '0', 103, 1, now(), NULL, NULL, '');
+insert into sys_role values('4', '000000', '浠呮湰浜�', 'test2', 4, '5', 't', 't', '0', '0', 103, 1, now(), NULL, NULL, '');
-- ----------------------------
-- 5銆佽彍鍗曟潈闄愯〃
-- ----------------------------
-drop table if exists sys_menu;
create table if not exists sys_menu
(
menu_id int8,
@@ -432,6 +431,7 @@
insert into sys_menu values('2', '绯荤粺鐩戞帶', '0', '3', 'monitor', null, '', '1', '0', 'M', '0', '0', '', 'monitor', 103, 1, now(), null, null, '绯荤粺鐩戞帶鐩綍');
insert into sys_menu values('3', '绯荤粺宸ュ叿', '0', '4', 'tool', null, '', '1', '0', 'M', '0', '0', '', 'tool', 103, 1, now(), null, null, '绯荤粺宸ュ叿鐩綍');
insert into sys_menu values('4', 'PLUS瀹樼綉', '0', '5', 'https://gitee.com/dromara/RuoYi-Vue-Plus', null, '', '0', '0', 'M', '0', '0', '', 'guide', 103, 1, now(), null, null, 'RuoYi-Vue-Plus瀹樼綉鍦板潃');
+insert into sys_menu VALUES('5', '娴嬭瘯鑿滃崟', '0', '5', 'demo', null, '', '1', '0', 'M', '0', '0', null, 'star', 103, 1, now(), null, null, '娴嬭瘯鑿滃崟');
-- 浜岀骇鑿滃崟
insert into sys_menu values('100', '鐢ㄦ埛绠$悊', '1', '1', 'user', 'system/user/index', '', '1', '0', 'C', '0', '0', 'system:user:list', 'user', 103, 1, now(), null, null, '鐢ㄦ埛绠$悊鑿滃崟');
insert into sys_menu values('101', '瑙掕壊绠$悊', '1', '2', 'role', 'system/role/index', '', '1', '0', 'C', '0', '0', 'system:role:list', 'peoples', 103, 1, now(), null, null, '瑙掕壊绠$悊鑿滃崟');
@@ -454,8 +454,8 @@
insert into sys_menu values('117', 'Admin鐩戞帶', '2', '5', 'Admin', 'monitor/admin/index', '', '1', '0', 'C', '0', '0', 'monitor:admin:list', 'dashboard', 103, 1, now(), null, null, 'Admin鐩戞帶鑿滃崟');
-- oss鑿滃崟
insert into sys_menu values('118', '鏂囦欢绠$悊', '1', '10', 'oss', 'system/oss/index', '', '1', '0', 'C', '0', '0', 'system:oss:list', 'upload', 103, 1, now(), null, null, '鏂囦欢绠$悊鑿滃崟');
--- powerjob server鎺у埗鍙�
-insert into sys_menu values('120', '浠诲姟璋冨害涓績', '2', '5', 'powerjob', 'monitor/powerjob/index', '', '1', '0', 'C', '0', '0', 'monitor:powerjob:list', 'job', 103, 1, now(), null, null, 'PowerJob鎺у埗鍙拌彍鍗�');
+-- snail-job server鎺у埗鍙�
+insert into sys_menu values('120', '浠诲姟璋冨害涓績', '2', '6', 'snailjob', 'monitor/snailjob/index', '', '1', '0', 'C', '0', '0', 'monitor:snailjob:list', 'job', 103, 1, now(), null, null, 'SnailJob鎺у埗鍙拌彍鍗�');
-- 涓夌骇鑿滃崟
insert into sys_menu values('500', '鎿嶄綔鏃ュ織', '108', '1', 'operlog', 'monitor/operlog/index', '', '1', '0', 'C', '0', '0', 'monitor:operlog:list', 'form', 103, 1, now(), null, null, '鎿嶄綔鏃ュ織鑿滃崟');
@@ -554,11 +554,24 @@
insert into sys_menu values('1063', '瀹㈡埛绔鐞嗕慨鏀�', '123', '3', '#', '', '', '1', '0', 'F', '0', '0', 'system:client:edit', '#', 103, 1, now(), null, null, '');
insert into sys_menu values('1064', '瀹㈡埛绔鐞嗗垹闄�', '123', '4', '#', '', '', '1', '0', 'F', '0', '0', 'system:client:remove', '#', 103, 1, now(), null, null, '');
insert into sys_menu values('1065', '瀹㈡埛绔鐞嗗鍑�', '123', '5', '#', '', '', '1', '0', 'F', '0', '0', 'system:client:export', '#', 103, 1, now(), null, null, '');
+-- 娴嬭瘯鑿滃崟
+INSERT INTO sys_menu VALUES('1500', '娴嬭瘯鍗曡〃', '5', '1', 'demo', 'demo/demo/index', '', '1', '0', 'C', '0', '0', 'demo:demo:list', '#', 103, 1, now(), NULL, NULL, '娴嬭瘯鍗曡〃鑿滃崟');
+INSERT INTO sys_menu VALUES('1501', '娴嬭瘯鍗曡〃鏌ヨ', '1500', '1', '#', '', '', '1', '0', 'F', '0', '0', 'demo:demo:query', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu VALUES('1502', '娴嬭瘯鍗曡〃鏂板', '1500', '2', '#', '', '', '1', '0', 'F', '0', '0', 'demo:demo:add', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu VALUES('1503', '娴嬭瘯鍗曡〃淇敼', '1500', '3', '#', '', '', '1', '0', 'F', '0', '0', 'demo:demo:edit', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu VALUES('1504', '娴嬭瘯鍗曡〃鍒犻櫎', '1500', '4', '#', '', '', '1', '0', 'F', '0', '0', 'demo:demo:remove', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu VALUES('1505', '娴嬭瘯鍗曡〃瀵煎嚭', '1500', '5', '#', '', '', '1', '0', 'F', '0', '0', 'demo:demo:export', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu VALUES('1506', '娴嬭瘯鏍戣〃', '5', '1', 'tree', 'demo/tree/index', '', '1', '0', 'C', '0', '0', 'demo:tree:list', '#', 103, 1, now(), NULL, NULL, '娴嬭瘯鏍戣〃鑿滃崟');
+INSERT INTO sys_menu VALUES('1507', '娴嬭瘯鏍戣〃鏌ヨ', '1506', '1', '#', '', '', '1', '0', 'F', '0', '0', 'demo:tree:query', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu VALUES('1508', '娴嬭瘯鏍戣〃鏂板', '1506', '2', '#', '', '', '1', '0', 'F', '0', '0', 'demo:tree:add', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu VALUES('1509', '娴嬭瘯鏍戣〃淇敼', '1506', '3', '#', '', '', '1', '0', 'F', '0', '0', 'demo:tree:edit', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu VALUES('1510', '娴嬭瘯鏍戣〃鍒犻櫎', '1506', '4', '#', '', '', '1', '0', 'F', '0', '0', 'demo:tree:remove', '#', 103, 1, now(), NULL, NULL, '');
+INSERT INTO sys_menu VALUES('1511', '娴嬭瘯鏍戣〃瀵煎嚭', '1506', '5', '#', '', '', '1', '0', 'F', '0', '0', 'demo:tree:export', '#', 103, 1, now(), NULL, NULL, '');
+
-- ----------------------------
-- 6銆佺敤鎴峰拰瑙掕壊鍏宠仈琛� 鐢ㄦ埛N-1瑙掕壊
-- ----------------------------
-drop table if exists sys_user_role;
create table if not exists sys_user_role
(
user_id int8 not null,
@@ -574,13 +587,12 @@
-- 鍒濆鍖�-鐢ㄦ埛鍜岃鑹插叧鑱旇〃鏁版嵁
-- ----------------------------
insert into sys_user_role values ('1', '1');
-insert into sys_user_role values ('2', '2');
-
+insert into sys_user_role values ('3', '3');
+insert into sys_user_role values ('4', '4');
-- ----------------------------
-- 7銆佽鑹插拰鑿滃崟鍏宠仈琛� 瑙掕壊1-N鑿滃崟
-- ----------------------------
-drop table if exists sys_role_menu;
create table if not exists sys_role_menu
(
role_id int8 not null,
@@ -595,95 +607,93 @@
-- ----------------------------
-- 鍒濆鍖�-瑙掕壊鍜岃彍鍗曞叧鑱旇〃鏁版嵁
-- ----------------------------
-insert into sys_role_menu values ('2', '1');
-insert into sys_role_menu values ('2', '2');
-insert into sys_role_menu values ('2', '3');
-insert into sys_role_menu values ('2', '4');
-insert into sys_role_menu values ('2', '100');
-insert into sys_role_menu values ('2', '101');
-insert into sys_role_menu values ('2', '102');
-insert into sys_role_menu values ('2', '103');
-insert into sys_role_menu values ('2', '104');
-insert into sys_role_menu values ('2', '105');
-insert into sys_role_menu values ('2', '106');
-insert into sys_role_menu values ('2', '107');
-insert into sys_role_menu values ('2', '108');
-insert into sys_role_menu values ('2', '109');
-insert into sys_role_menu values ('2', '110');
-insert into sys_role_menu values ('2', '111');
-insert into sys_role_menu values ('2', '112');
-insert into sys_role_menu values ('2', '113');
-insert into sys_role_menu values ('2', '114');
-insert into sys_role_menu values ('2', '115');
-insert into sys_role_menu values ('2', '116');
-insert into sys_role_menu values ('2', '500');
-insert into sys_role_menu values ('2', '501');
-insert into sys_role_menu values ('2', '1000');
-insert into sys_role_menu values ('2', '1001');
-insert into sys_role_menu values ('2', '1002');
-insert into sys_role_menu values ('2', '1003');
-insert into sys_role_menu values ('2', '1004');
-insert into sys_role_menu values ('2', '1005');
-insert into sys_role_menu values ('2', '1006');
-insert into sys_role_menu values ('2', '1007');
-insert into sys_role_menu values ('2', '1008');
-insert into sys_role_menu values ('2', '1009');
-insert into sys_role_menu values ('2', '1010');
-insert into sys_role_menu values ('2', '1011');
-insert into sys_role_menu values ('2', '1012');
-insert into sys_role_menu values ('2', '1013');
-insert into sys_role_menu values ('2', '1014');
-insert into sys_role_menu values ('2', '1015');
-insert into sys_role_menu values ('2', '1016');
-insert into sys_role_menu values ('2', '1017');
-insert into sys_role_menu values ('2', '1018');
-insert into sys_role_menu values ('2', '1019');
-insert into sys_role_menu values ('2', '1020');
-insert into sys_role_menu values ('2', '1021');
-insert into sys_role_menu values ('2', '1022');
-insert into sys_role_menu values ('2', '1023');
-insert into sys_role_menu values ('2', '1024');
-insert into sys_role_menu values ('2', '1025');
-insert into sys_role_menu values ('2', '1026');
-insert into sys_role_menu values ('2', '1027');
-insert into sys_role_menu values ('2', '1028');
-insert into sys_role_menu values ('2', '1029');
-insert into sys_role_menu values ('2', '1030');
-insert into sys_role_menu values ('2', '1031');
-insert into sys_role_menu values ('2', '1032');
-insert into sys_role_menu values ('2', '1033');
-insert into sys_role_menu values ('2', '1034');
-insert into sys_role_menu values ('2', '1035');
-insert into sys_role_menu values ('2', '1036');
-insert into sys_role_menu values ('2', '1037');
-insert into sys_role_menu values ('2', '1038');
-insert into sys_role_menu values ('2', '1039');
-insert into sys_role_menu values ('2', '1040');
-insert into sys_role_menu values ('2', '1041');
-insert into sys_role_menu values ('2', '1042');
-insert into sys_role_menu values ('2', '1043');
-insert into sys_role_menu values ('2', '1044');
-insert into sys_role_menu values ('2', '1045');
-insert into sys_role_menu values ('2', '1050');
-insert into sys_role_menu values ('2', '1046');
-insert into sys_role_menu values ('2', '1047');
-insert into sys_role_menu values ('2', '1048');
-insert into sys_role_menu values ('2', '1055');
-insert into sys_role_menu values ('2', '1056');
-insert into sys_role_menu values ('2', '1057');
-insert into sys_role_menu values ('2', '1058');
-insert into sys_role_menu values ('2', '1059');
-insert into sys_role_menu values ('2', '1060');
-insert into sys_role_menu values ('2', '1061');
-insert into sys_role_menu values ('2', '1062');
-insert into sys_role_menu values ('2', '1063');
-insert into sys_role_menu values ('2', '1064');
-insert into sys_role_menu values ('2', '1065');
+insert into sys_role_menu values ('3', '1');
+insert into sys_role_menu values ('3', '5');
+insert into sys_role_menu values ('3', '100');
+insert into sys_role_menu values ('3', '101');
+insert into sys_role_menu values ('3', '102');
+insert into sys_role_menu values ('3', '103');
+insert into sys_role_menu values ('3', '104');
+insert into sys_role_menu values ('3', '105');
+insert into sys_role_menu values ('3', '106');
+insert into sys_role_menu values ('3', '107');
+insert into sys_role_menu values ('3', '108');
+insert into sys_role_menu values ('3', '500');
+insert into sys_role_menu values ('3', '501');
+insert into sys_role_menu values ('3', '1001');
+insert into sys_role_menu values ('3', '1002');
+insert into sys_role_menu values ('3', '1003');
+insert into sys_role_menu values ('3', '1004');
+insert into sys_role_menu values ('3', '1005');
+insert into sys_role_menu values ('3', '1006');
+insert into sys_role_menu values ('3', '1007');
+insert into sys_role_menu values ('3', '1008');
+insert into sys_role_menu values ('3', '1009');
+insert into sys_role_menu values ('3', '1010');
+insert into sys_role_menu values ('3', '1011');
+insert into sys_role_menu values ('3', '1012');
+insert into sys_role_menu values ('3', '1013');
+insert into sys_role_menu values ('3', '1014');
+insert into sys_role_menu values ('3', '1015');
+insert into sys_role_menu values ('3', '1016');
+insert into sys_role_menu values ('3', '1017');
+insert into sys_role_menu values ('3', '1018');
+insert into sys_role_menu values ('3', '1019');
+insert into sys_role_menu values ('3', '1020');
+insert into sys_role_menu values ('3', '1021');
+insert into sys_role_menu values ('3', '1022');
+insert into sys_role_menu values ('3', '1023');
+insert into sys_role_menu values ('3', '1024');
+insert into sys_role_menu values ('3', '1025');
+insert into sys_role_menu values ('3', '1026');
+insert into sys_role_menu values ('3', '1027');
+insert into sys_role_menu values ('3', '1028');
+insert into sys_role_menu values ('3', '1029');
+insert into sys_role_menu values ('3', '1030');
+insert into sys_role_menu values ('3', '1031');
+insert into sys_role_menu values ('3', '1032');
+insert into sys_role_menu values ('3', '1033');
+insert into sys_role_menu values ('3', '1034');
+insert into sys_role_menu values ('3', '1035');
+insert into sys_role_menu values ('3', '1036');
+insert into sys_role_menu values ('3', '1037');
+insert into sys_role_menu values ('3', '1038');
+insert into sys_role_menu values ('3', '1039');
+insert into sys_role_menu values ('3', '1040');
+insert into sys_role_menu values ('3', '1041');
+insert into sys_role_menu values ('3', '1042');
+insert into sys_role_menu values ('3', '1043');
+insert into sys_role_menu values ('3', '1044');
+insert into sys_role_menu values ('3', '1045');
+insert into sys_role_menu values ('3', '1500');
+insert into sys_role_menu values ('3', '1501');
+insert into sys_role_menu values ('3', '1502');
+insert into sys_role_menu values ('3', '1503');
+insert into sys_role_menu values ('3', '1504');
+insert into sys_role_menu values ('3', '1505');
+insert into sys_role_menu values ('3', '1506');
+insert into sys_role_menu values ('3', '1507');
+insert into sys_role_menu values ('3', '1508');
+insert into sys_role_menu values ('3', '1509');
+insert into sys_role_menu values ('3', '1510');
+insert into sys_role_menu values ('3', '1511');
+insert into sys_role_menu values ('4', '5');
+insert into sys_role_menu values ('4', '1500');
+insert into sys_role_menu values ('4', '1501');
+insert into sys_role_menu values ('4', '1502');
+insert into sys_role_menu values ('4', '1503');
+insert into sys_role_menu values ('4', '1504');
+insert into sys_role_menu values ('4', '1505');
+insert into sys_role_menu values ('4', '1506');
+insert into sys_role_menu values ('4', '1507');
+insert into sys_role_menu values ('4', '1508');
+insert into sys_role_menu values ('4', '1509');
+insert into sys_role_menu values ('4', '1510');
+insert into sys_role_menu values ('4', '1511');
-- ----------------------------
-- 8銆佽鑹插拰閮ㄩ棬鍏宠仈琛� 瑙掕壊1-N閮ㄩ棬
-- ----------------------------
-drop table if exists sys_role_dept;
create table if not exists sys_role_dept
(
role_id int8 not null,
@@ -695,18 +705,10 @@
comment on column sys_role_dept.role_id is '瑙掕壊ID';
comment on column sys_role_dept.dept_id is '閮ㄩ棬ID';
--- ----------------------------
--- 鍒濆鍖�-瑙掕壊鍜岄儴闂ㄥ叧鑱旇〃鏁版嵁
--- ----------------------------
-insert into sys_role_dept values ('2', '100');
-insert into sys_role_dept values ('2', '101');
-insert into sys_role_dept values ('2', '105');
-
-- ----------------------------
-- 9銆佺敤鎴蜂笌宀椾綅鍏宠仈琛� 鐢ㄦ埛1-N宀椾綅
-- ----------------------------
-drop table if exists sys_user_post;
create table if not exists sys_user_post
(
user_id int8 not null,
@@ -722,13 +724,10 @@
-- 鍒濆鍖�-鐢ㄦ埛涓庡矖浣嶅叧鑱旇〃鏁版嵁
-- ----------------------------
insert into sys_user_post values ('1', '1');
-insert into sys_user_post values ('2', '2');
-
-- ----------------------------
-- 10銆佹搷浣滄棩蹇楄褰�
-- ----------------------------
-drop table if exists sys_oper_log;
create table if not exists sys_oper_log
(
oper_id int8,
@@ -779,7 +778,6 @@
-- ----------------------------
-- 11銆佸瓧鍏哥被鍨嬭〃
-- ----------------------------
-drop table if exists sys_dict_type;
create table if not exists sys_dict_type
(
dict_id int8,
@@ -823,7 +821,6 @@
-- ----------------------------
-- 12銆佸瓧鍏告暟鎹〃
-- ----------------------------
-drop table if exists sys_dict_data;
create table if not exists sys_dict_data
(
dict_code int8,
@@ -900,7 +897,6 @@
-- ----------------------------
-- 13銆佸弬鏁伴厤缃〃
-- ----------------------------
-drop table if exists sys_config;
create table if not exists sys_config
(
config_id int8,
@@ -942,7 +938,6 @@
-- ----------------------------
-- 14銆佺郴缁熻闂褰�
-- ----------------------------
-drop table if exists sys_logininfor;
create table if not exists sys_logininfor
(
info_id int8,
@@ -980,7 +975,6 @@
-- ----------------------------
-- 17銆侀�氱煡鍏憡琛�
-- ----------------------------
-drop table if exists sys_notice;
create table if not exists sys_notice
(
notice_id int8,
@@ -1022,7 +1016,6 @@
-- ----------------------------
-- 18銆佷唬鐮佺敓鎴愪笟鍔¤〃
-- ----------------------------
-drop table if exists gen_table;
create table if not exists gen_table
(
table_id int8,
@@ -1077,7 +1070,6 @@
-- ----------------------------
-- 19銆佷唬鐮佺敓鎴愪笟鍔¤〃瀛楁
-- ----------------------------
-drop table if exists gen_table_column;
create table if not exists gen_table_column
(
column_id int8,
@@ -1134,7 +1126,6 @@
-- ----------------------------
-- OSS瀵硅薄瀛樺偍琛�
-- ----------------------------
-drop table if exists sys_oss;
create table if not exists sys_oss
(
oss_id int8,
@@ -1169,7 +1160,6 @@
-- ----------------------------
-- OSS瀵硅薄瀛樺偍鍔ㄦ�侀厤缃〃
-- ----------------------------
-drop table if exists sys_oss_config;
create table if not exists sys_oss_config
(
oss_config_id int8,
@@ -1196,7 +1186,7 @@
);
comment on table sys_oss_config is '瀵硅薄瀛樺偍閰嶇疆琛�';
-comment on column sys_oss_config.oss_config_id is '涓诲缓';
+comment on column sys_oss_config.oss_config_id is '涓婚敭';
comment on column sys_oss_config.tenant_id is '绉熸埛缂栫爜';
comment on column sys_oss_config.config_key is '閰嶇疆key';
comment on column sys_oss_config.access_key is 'accessKey';
@@ -1226,7 +1216,6 @@
-- ----------------------------
-- 绯荤粺鎺堟潈琛�
-- ----------------------------
-drop table if exists sys_client;
create table sys_client (
id int8,
client_id varchar(64) default ''::varchar,
@@ -1247,7 +1236,7 @@
);
comment on table sys_client is '绯荤粺鎺堟潈琛�';
-comment on column sys_client.id is '涓诲缓';
+comment on column sys_client.id is '涓婚敭';
comment on column sys_client.client_id is '瀹㈡埛绔痠d';
comment on column sys_client.client_key is '瀹㈡埛绔痥ey';
comment on column sys_client.client_secret is '瀹㈡埛绔閽�';
@@ -1266,6 +1255,100 @@
insert into sys_client values (1, 'e5cd7e4891bf95d1d19206ce24a7b32e', 'pc', 'pc123', 'password,social', 'pc', 1800, 604800, 0, 0, 103, 1, now(), 1, now());
insert into sys_client values (2, '428a8310cd442757ae699df5d894f051', 'app', 'app123', 'password,sms,social', 'android', 1800, 604800, 0, 0, 103, 1, now(), 1, now());
+create table if not exists test_demo
+(
+ id int8,
+ tenant_id varchar(20) default '000000',
+ dept_id int8,
+ user_id int8,
+ order_num int4 default 0,
+ test_key varchar(255),
+ value varchar(255),
+ version int4 default 0,
+ create_dept int8,
+ create_time timestamp,
+ create_by int8,
+ update_time timestamp,
+ update_by int8,
+ del_flag int4 default 0
+);
+
+comment on table test_demo is '娴嬭瘯鍗曡〃';
+comment on column test_demo.id is '涓婚敭';
+comment on column test_demo.tenant_id is '绉熸埛缂栧彿';
+comment on column test_demo.dept_id is '閮ㄩ棬id';
+comment on column test_demo.user_id is '鐢ㄦ埛id';
+comment on column test_demo.order_num is '鎺掑簭鍙�';
+comment on column test_demo.test_key is 'key閿�';
+comment on column test_demo.value is '鍊�';
+comment on column test_demo.version is '鐗堟湰';
+comment on column test_demo.create_dept is '鍒涘缓閮ㄩ棬';
+comment on column test_demo.create_time is '鍒涘缓鏃堕棿';
+comment on column test_demo.create_by is '鍒涘缓浜�';
+comment on column test_demo.update_time is '鏇存柊鏃堕棿';
+comment on column test_demo.update_by is '鏇存柊浜�';
+comment on column test_demo.del_flag is '鍒犻櫎鏍囧織';
+
+create table if not exists test_tree
+(
+ id int8,
+ tenant_id varchar(20) default '000000',
+ parent_id int8 default 0,
+ dept_id int8,
+ user_id int8,
+ tree_name varchar(255),
+ version int4 default 0,
+ create_dept int8,
+ create_time timestamp,
+ create_by int8,
+ update_time timestamp,
+ update_by int8,
+ del_flag integer default 0
+);
+
+comment on table test_tree is '娴嬭瘯鏍戣〃';
+comment on column test_tree.id is '涓婚敭';
+comment on column test_tree.tenant_id is '绉熸埛缂栧彿';
+comment on column test_tree.parent_id is '鐖秈d';
+comment on column test_tree.dept_id is '閮ㄩ棬id';
+comment on column test_tree.user_id is '鐢ㄦ埛id';
+comment on column test_tree.tree_name is '鍊�';
+comment on column test_tree.version is '鐗堟湰';
+comment on column test_tree.create_dept is '鍒涘缓閮ㄩ棬';
+comment on column test_tree.create_time is '鍒涘缓鏃堕棿';
+comment on column test_tree.create_by is '鍒涘缓浜�';
+comment on column test_tree.update_time is '鏇存柊鏃堕棿';
+comment on column test_tree.update_by is '鏇存柊浜�';
+comment on column test_tree.del_flag is '鍒犻櫎鏍囧織';
+
+INSERT INTO test_demo VALUES (1, '000000', 102, 4, 1, '娴嬭瘯鏁版嵁鏉冮檺', '娴嬭瘯', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (2, '000000', 102, 3, 2, '瀛愯妭鐐�1', '111', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (3, '000000', 102, 3, 3, '瀛愯妭鐐�2', '222', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (4, '000000', 108, 4, 4, '娴嬭瘯鏁版嵁', 'demo', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (5, '000000', 108, 3, 13, '瀛愯妭鐐�11', '1111', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (6, '000000', 108, 3, 12, '瀛愯妭鐐�22', '2222', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (7, '000000', 108, 3, 11, '瀛愯妭鐐�33', '3333', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (8, '000000', 108, 3, 10, '瀛愯妭鐐�44', '4444', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (9, '000000', 108, 3, 9, '瀛愯妭鐐�55', '5555', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (10, '000000', 108, 3, 8, '瀛愯妭鐐�66', '6666', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (11, '000000', 108, 3, 7, '瀛愯妭鐐�77', '7777', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (12, '000000', 108, 3, 6, '瀛愯妭鐐�88', '8888', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (13, '000000', 108, 3, 5, '瀛愯妭鐐�99', '9999', 0, 103, now(), 1, NULL, NULL, 0);
+
+INSERT INTO test_tree VALUES (1, '000000', 0, 102, 4, '娴嬭瘯鏁版嵁鏉冮檺', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (2, '000000', 1, 102, 3, '瀛愯妭鐐�1', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (3, '000000', 2, 102, 3, '瀛愯妭鐐�2', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (4, '000000', 0, 108, 4, '娴嬭瘯鏍�1', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (5, '000000', 4, 108, 3, '瀛愯妭鐐�11', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (6, '000000', 4, 108, 3, '瀛愯妭鐐�22', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (7, '000000', 4, 108, 3, '瀛愯妭鐐�33', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (8, '000000', 5, 108, 3, '瀛愯妭鐐�44', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (9, '000000', 6, 108, 3, '瀛愯妭鐐�55', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (10, '000000', 7, 108, 3, '瀛愯妭鐐�66', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (11, '000000', 7, 108, 3, '瀛愯妭鐐�77', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (12, '000000', 10, 108, 3, '瀛愯妭鐐�88', 0, 103, now(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (13, '000000', 10, 108, 3, '瀛愯妭鐐�99', 0, 103, now(), 1, NULL, NULL, 0);
+
-- 瀛楃涓茶嚜鍔ㄨ浆鏃堕棿 閬垮厤妗嗘灦鏃堕棿鏌ヨ鎶ラ敊闂
create or replace function cast_varchar_to_timestamp(varchar) returns timestamptz as $$
select to_timestamp($1, 'yyyy-mm-dd hh24:mi:ss');
diff --git a/script/sql/postgres/postgres_test.sql b/script/sql/postgres/postgres_test.sql
deleted file mode 100644
index 179096b..0000000
--- a/script/sql/postgres/postgres_test.sql
+++ /dev/null
@@ -1,204 +0,0 @@
-DROP TABLE if EXISTS test_demo;
-create table if not exists test_demo
-(
- id int8,
- tenant_id varchar(20) default '000000',
- dept_id int8,
- user_id int8,
- order_num int4 default 0,
- test_key varchar(255),
- value varchar(255),
- version int4 default 0,
- create_time timestamp,
- create_dept int8,
- create_by int8,
- update_time timestamp,
- update_by int8,
- del_flag int4 default 0
-);
-
-comment on table test_demo is '娴嬭瘯鍗曡〃';
-comment on column test_demo.id is '涓婚敭';
-comment on column test_demo.tenant_id is '绉熸埛缂栧彿';
-comment on column test_demo.dept_id is '閮ㄩ棬id';
-comment on column test_demo.user_id is '鐢ㄦ埛id';
-comment on column test_demo.order_num is '鎺掑簭鍙�';
-comment on column test_demo.test_key is 'key閿�';
-comment on column test_demo.value is '鍊�';
-comment on column test_demo.version is '鐗堟湰';
-comment on column test_demo.create_dept is '鍒涘缓閮ㄩ棬';
-comment on column test_demo.create_time is '鍒涘缓鏃堕棿';
-comment on column test_demo.create_by is '鍒涘缓浜�';
-comment on column test_demo.update_time is '鏇存柊鏃堕棿';
-comment on column test_demo.update_by is '鏇存柊浜�';
-comment on column test_demo.del_flag is '鍒犻櫎鏍囧織';
-
-DROP TABLE if EXISTS test_tree;
-create table if not exists test_tree
-(
- id int8,
- tenant_id varchar(20) default '000000',
- parent_id int8 default 0,
- dept_id int8,
- user_id int8,
- tree_name varchar(255),
- version int4 default 0,
- create_time timestamp,
- create_dept int8,
- create_by int8,
- update_time timestamp,
- update_by int8,
- del_flag integer default 0
-);
-
-comment on table test_tree is '娴嬭瘯鏍戣〃';
-comment on column test_tree.id is '涓婚敭';
-comment on column test_tree.tenant_id is '绉熸埛缂栧彿';
-comment on column test_tree.parent_id is '鐖秈d';
-comment on column test_tree.dept_id is '閮ㄩ棬id';
-comment on column test_tree.user_id is '鐢ㄦ埛id';
-comment on column test_tree.tree_name is '鍊�';
-comment on column test_tree.version is '鐗堟湰';
-comment on column test_tree.create_dept is '鍒涘缓閮ㄩ棬';
-comment on column test_tree.create_time is '鍒涘缓鏃堕棿';
-comment on column test_tree.create_by is '鍒涘缓浜�';
-comment on column test_tree.update_time is '鏇存柊鏃堕棿';
-comment on column test_tree.update_by is '鏇存柊浜�';
-comment on column test_tree.del_flag is '鍒犻櫎鏍囧織';
-
-INSERT INTO sys_user(user_id, tenant_id, dept_id, user_name, nick_name, user_type, email, phonenumber, sex, avatar, password, status, del_flag, login_ip, login_date, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (3, '000000', 108, 'test', '鏈儴闂ㄥ強浠ヤ笅 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', now(), 103, 1, now(), 3, now(), NULL);
-INSERT INTO sys_user(user_id, tenant_id, dept_id, user_name, nick_name, user_type, email, phonenumber, sex, avatar, password, status, del_flag, login_ip, login_date, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (4, '000000', 102, 'test1', '浠呮湰浜� 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', now(), 103, 1, now(), 4, now(), NULL);
-
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (5, '娴嬭瘯鑿滃崟', 0, 5, 'demo', NULL, 1, 0, 'M', '0', '0', NULL, 'star', 103, 1, now(), NULL, NULL, '');
-
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1500, '娴嬭瘯鍗曡〃', 5, 1, 'demo', 'demo/demo/index', 1, 0, 'C', '0', '0', 'demo:demo:list', '#', 103, 1, now(), NULL, NULL, '娴嬭瘯鍗曡〃鑿滃崟');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1501, '娴嬭瘯鍗曡〃鏌ヨ', 1500, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:query', '#', 103, 1, now(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1502, '娴嬭瘯鍗曡〃鏂板', 1500, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:add', '#', 103, 1, now(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1503, '娴嬭瘯鍗曡〃淇敼', 1500, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:edit', '#', 103, 1, now(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1504, '娴嬭瘯鍗曡〃鍒犻櫎', 1500, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:remove', '#', 103, 1, now(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1505, '娴嬭瘯鍗曡〃瀵煎嚭', 1500, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:export', '#', 103, 1, now(), NULL, NULL, '');
-
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1506, '娴嬭瘯鏍戣〃', 5, 1, 'tree', 'demo/tree/index', 1, 0, 'C', '0', '0', 'demo:tree:list', '#', 103, 1, now(), NULL, NULL, '娴嬭瘯鏍戣〃鑿滃崟');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1507, '娴嬭瘯鏍戣〃鏌ヨ', 1506, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:query', '#', 103, 1, now(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1508, '娴嬭瘯鏍戣〃鏂板', 1506, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:add', '#', 103, 1, now(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1509, '娴嬭瘯鏍戣〃淇敼', 1506, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:edit', '#', 103, 1, now(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1510, '娴嬭瘯鏍戣〃鍒犻櫎', 1506, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:remove', '#', 103, 1, now(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1511, '娴嬭瘯鏍戣〃瀵煎嚭', 1506, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:export', '#', 103, 1, now(), NULL, NULL, '');
-
-INSERT INTO sys_role(role_id, tenant_id, role_name, role_key, role_sort, data_scope, menu_check_strictly, dept_check_strictly, status, del_flag, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (3, '000000', '鏈儴闂ㄥ強浠ヤ笅', 'test1', 3, '4', 't', 't', '0', '0', 103, 1, now(), 1, NULL, NULL);
-INSERT INTO sys_role(role_id, tenant_id, role_name, role_key, role_sort, data_scope, menu_check_strictly, dept_check_strictly, status, del_flag, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (4, '000000', '浠呮湰浜�', 'test2', 4, '5', 't', 't', '0', '0', 103, 1, now(), 1, NULL, NULL);
-
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 5);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 100);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 101);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 102);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 103);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 104);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 105);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 106);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 107);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 108);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 500);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 501);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1001);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1002);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1003);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1004);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1005);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1006);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1007);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1008);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1009);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1010);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1011);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1012);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1013);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1014);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1015);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1016);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1017);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1018);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1019);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1020);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1021);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1022);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1023);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1024);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1025);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1026);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1027);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1028);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1029);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1030);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1031);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1032);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1033);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1034);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1035);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1036);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1037);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1038);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1039);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1040);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1041);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1042);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1043);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1044);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1045);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1500);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1501);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1502);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1503);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1504);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1505);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1506);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1507);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1508);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1509);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1510);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1511);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 5);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1500);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1501);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1502);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1503);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1504);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1505);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1506);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1507);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1508);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1509);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1510);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1511);
-
-INSERT INTO sys_user_role(user_id, role_id) VALUES (3, 3);
-INSERT INTO sys_user_role(user_id, role_id) VALUES (4, 4);
-
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (1, '000000', 102, 4, 1, '娴嬭瘯鏁版嵁鏉冮檺', '娴嬭瘯', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (2, '000000', 102, 3, 2, '瀛愯妭鐐�1', '111', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (3, '000000', 102, 3, 3, '瀛愯妭鐐�2', '222', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (4, '000000', 108, 4, 4, '娴嬭瘯鏁版嵁', 'demo', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (5, '000000', 108, 3, 13, '瀛愯妭鐐�11', '1111', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (6, '000000', 108, 3, 12, '瀛愯妭鐐�22', '2222', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (7, '000000', 108, 3, 11, '瀛愯妭鐐�33', '3333', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (8, '000000', 108, 3, 10, '瀛愯妭鐐�44', '4444', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (9, '000000', 108, 3, 9, '瀛愯妭鐐�55', '5555', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (10, '000000', 108, 3, 8, '瀛愯妭鐐�66', '6666', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (11, '000000', 108, 3, 7, '瀛愯妭鐐�77', '7777', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (12, '000000', 108, 3, 6, '瀛愯妭鐐�88', '8888', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (13, '000000', 108, 3, 5, '瀛愯妭鐐�99', '9999', 0, 103, now(), 1, NULL, NULL, 0);
-
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (1, '000000', 0, 102, 4, '娴嬭瘯鏁版嵁鏉冮檺', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (2, '000000', 1, 102, 3, '瀛愯妭鐐�1', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (3, '000000', 2, 102, 3, '瀛愯妭鐐�2', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (4, '000000', 0, 108, 4, '娴嬭瘯鏍�1', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (5, '000000', 4, 108, 3, '瀛愯妭鐐�11', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (6, '000000', 4, 108, 3, '瀛愯妭鐐�22', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (7, '000000', 4, 108, 3, '瀛愯妭鐐�33', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (8, '000000', 5, 108, 3, '瀛愯妭鐐�44', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (9, '000000', 6, 108, 3, '瀛愯妭鐐�55', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (10, '000000', 7, 108, 3, '瀛愯妭鐐�66', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (11, '000000', 7, 108, 3, '瀛愯妭鐐�77', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (12, '000000', 10, 108, 3, '瀛愯妭鐐�88', 0, 103, now(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (13, '000000', 10, 108, 3, '瀛愯妭鐐�99', 0, 103, now(), 1, NULL, NULL, 0);
diff --git a/script/sql/postgres/powerjob.sql b/script/sql/postgres/powerjob.sql
deleted file mode 100644
index 56d3bcb..0000000
--- a/script/sql/postgres/powerjob.sql
+++ /dev/null
@@ -1,258 +0,0 @@
--- pj_app_info definition
-
--- Drop table
-
--- DROP TABLE pj_app_info;
-
-CREATE TABLE pj_app_info (
- id int8 NOT NULL,
- app_name varchar(255) NULL,
- current_server varchar(255) NULL,
- gmt_create timestamp NULL,
- gmt_modified timestamp NULL,
- "password" varchar(255) NULL,
- CONSTRAINT pj_app_info_pkey PRIMARY KEY (id),
- CONSTRAINT uidx01_app_info UNIQUE (app_name)
-);
-
-INSERT INTO pj_app_info VALUES(1, 'ruoyi-worker', '127.0.0.1:10010', '2023-06-13 16:32:59.263', '2023-07-04 17:25:49.798', '123456');
-
-
-
--- pj_container_info definition
-
--- Drop table
-
--- DROP TABLE pj_container_info;
-
-CREATE TABLE pj_container_info (
- id int8 NOT NULL,
- app_id int8 NULL,
- container_name varchar(255) NULL,
- gmt_create timestamp NULL,
- gmt_modified timestamp NULL,
- last_deploy_time timestamp NULL,
- source_info varchar(255) NULL,
- source_type int4 NULL,
- status int4 NULL,
- "version" varchar(255) NULL,
- CONSTRAINT pj_container_info_pkey PRIMARY KEY (id)
-);
-CREATE INDEX idx01_container_info ON pj_container_info USING btree (app_id);
-
-
--- pj_instance_info definition
-
--- Drop table
-
--- DROP TABLE pj_instance_info;
-
-CREATE TABLE pj_instance_info (
- id int8 NOT NULL,
- actual_trigger_time int8 NULL,
- app_id int8 NULL,
- expected_trigger_time int8 NULL,
- finished_time int8 NULL,
- gmt_create timestamp NULL,
- gmt_modified timestamp NULL,
- instance_id int8 NULL,
- instance_params oid NULL,
- job_id int8 NULL,
- job_params oid NULL,
- last_report_time int8 NULL,
- "result" oid NULL,
- running_times int8 NULL,
- status int4 NULL,
- task_tracker_address varchar(255) NULL,
- "type" int4 NULL,
- wf_instance_id int8 NULL,
- CONSTRAINT pj_instance_info_pkey PRIMARY KEY (id)
-);
-CREATE INDEX idx01_instance_info ON pj_instance_info USING btree (job_id, status);
-CREATE INDEX idx02_instance_info ON pj_instance_info USING btree (app_id, status);
-CREATE INDEX idx03_instance_info ON pj_instance_info USING btree (instance_id, status);
-
-
--- pj_job_info definition
-
--- Drop table
-
--- DROP TABLE pj_job_info;
-
-CREATE TABLE pj_job_info (
- id int8 NOT NULL,
- alarm_config varchar(255) NULL,
- app_id int8 NULL,
- concurrency int4 NULL,
- designated_workers varchar(255) NULL,
- dispatch_strategy int4 NULL,
- execute_type int4 NULL,
- extra varchar(255) NULL,
- gmt_create timestamp NULL,
- gmt_modified timestamp NULL,
- instance_retry_num int4 NULL,
- instance_time_limit int8 NULL,
- job_description varchar(255) NULL,
- job_name varchar(255) NULL,
- job_params oid NULL,
- lifecycle varchar(255) NULL,
- log_config varchar(255) NULL,
- max_instance_num int4 NULL,
- max_worker_count int4 NULL,
- min_cpu_cores float8 NOT NULL,
- min_disk_space float8 NOT NULL,
- min_memory_space float8 NOT NULL,
- next_trigger_time int8 NULL,
- notify_user_ids varchar(255) NULL,
- processor_info varchar(255) NULL,
- processor_type int4 NULL,
- status int4 NULL,
- tag varchar(255) NULL,
- task_retry_num int4 NULL,
- time_expression varchar(255) NULL,
- time_expression_type int4 NULL,
- CONSTRAINT pj_job_info_pkey PRIMARY KEY (id)
-);
-CREATE INDEX idx01_job_info ON pj_job_info USING btree (app_id, status, time_expression_type, next_trigger_time);
-
-
-INSERT INTO pj_job_info VALUES(1, '{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', 1, 5, '', 2, 1, NULL, '2023-06-02 15:01:27.717', '2023-07-04 17:22:12.374', 1, 0, '', '鍗曟満澶勭悊鍣ㄦ墽琛屾祴璇�', NULL, '{}', '{"type":1}', 0, 0, 0.0, 0.0, 0.0, NULL, NULL, 'org.dromara.job.processors.StandaloneProcessorDemo', 1, 2, NULL, 1, '30000', 3);
-INSERT INTO pj_job_info VALUES(2, '{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', 1, 5, '', 1, 2, NULL, '2023-06-02 15:04:45.342', '2023-07-04 17:22:12.816', 0, 0, NULL, '骞挎挱澶勭悊鍣ㄦ祴璇�', NULL, '{}', '{"type":1}', 0, 0, 0.0, 0.0, 0.0, NULL, NULL, 'org.dromara.job.processors.BroadcastProcessorDemo', 1, 2, NULL, 1, '30000', 3);
-INSERT INTO pj_job_info VALUES(3, '{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', 1, 5, '', 1, 4, NULL, '2023-06-02 15:13:23.519', '2023-06-02 16:03:22.421', 0, 0, NULL, 'Map澶勭悊鍣ㄦ祴璇�', NULL, '{}', '{"type":1}', 0, 0, 0.0, 0.0, 0.0, NULL, NULL, 'org.dromara.job.processors.MapProcessorDemo', 1, 2, NULL, 1, '1000', 3);
-INSERT INTO pj_job_info VALUES(4, '{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', 1, 5, '', 1, 3, NULL, '2023-06-02 15:45:25.896', '2023-06-02 16:03:23.125', 0, 0, NULL, 'MapReduce澶勭悊鍣ㄦ祴璇�', NULL, '{}', '{"type":1}', 0, 0, 0.0, 0.0, 0.0, NULL, NULL, 'org.dromara.job.processors.MapReduceProcessorDemo', 1, 2, NULL, 1, '1000', 3);
-
-
--- pj_oms_lock definition
-
--- Drop table
-
--- DROP TABLE pj_oms_lock;
-
-CREATE TABLE pj_oms_lock (
- id int8 NOT NULL,
- gmt_create timestamp NULL,
- gmt_modified timestamp NULL,
- lock_name varchar(255) NULL,
- max_lock_time int8 NULL,
- ownerip varchar(255) NULL,
- CONSTRAINT pj_oms_lock_pkey PRIMARY KEY (id),
- CONSTRAINT uidx01_oms_lock UNIQUE (lock_name)
-);
-
-
--- pj_server_info definition
-
--- Drop table
-
--- DROP TABLE pj_server_info;
-
-CREATE TABLE pj_server_info (
- id int8 NOT NULL,
- gmt_create timestamp NULL,
- gmt_modified timestamp NULL,
- ip varchar(255) NULL,
- CONSTRAINT pj_server_info_pkey PRIMARY KEY (id),
- CONSTRAINT uidx01_server_info UNIQUE (ip)
-);
-CREATE INDEX idx01_server_info ON pj_server_info USING btree (gmt_modified);
-
-
--- pj_user_info definition
-
--- Drop table
-
--- DROP TABLE pj_user_info;
-
-CREATE TABLE pj_user_info (
- id int8 NOT NULL,
- email varchar(255) NULL,
- extra varchar(255) NULL,
- gmt_create timestamp NULL,
- gmt_modified timestamp NULL,
- "password" varchar(255) NULL,
- phone varchar(255) NULL,
- username varchar(255) NULL,
- web_hook varchar(255) NULL,
- CONSTRAINT pj_user_info_pkey PRIMARY KEY (id)
-);
-CREATE INDEX uidx01_user_info ON pj_user_info USING btree (username);
-CREATE INDEX uidx02_user_info ON pj_user_info USING btree (email);
-
-
--- pj_workflow_info definition
-
--- Drop table
-
--- DROP TABLE pj_workflow_info;
-
-CREATE TABLE pj_workflow_info (
- id int8 NOT NULL,
- app_id int8 NULL,
- extra varchar(255) NULL,
- gmt_create timestamp NULL,
- gmt_modified timestamp NULL,
- lifecycle varchar(255) NULL,
- max_wf_instance_num int4 NULL,
- next_trigger_time int8 NULL,
- notify_user_ids varchar(255) NULL,
- pedag oid NULL,
- status int4 NULL,
- time_expression varchar(255) NULL,
- time_expression_type int4 NULL,
- wf_description varchar(255) NULL,
- wf_name varchar(255) NULL,
- CONSTRAINT pj_workflow_info_pkey PRIMARY KEY (id)
-);
-CREATE INDEX idx01_workflow_info ON pj_workflow_info USING btree (app_id, status, time_expression_type, next_trigger_time);
-
-
--- pj_workflow_instance_info definition
-
--- Drop table
-
--- DROP TABLE pj_workflow_instance_info;
-
-CREATE TABLE pj_workflow_instance_info (
- id int8 NOT NULL,
- actual_trigger_time int8 NULL,
- app_id int8 NULL,
- dag oid NULL,
- expected_trigger_time int8 NULL,
- finished_time int8 NULL,
- gmt_create timestamp NULL,
- gmt_modified timestamp NULL,
- parent_wf_instance_id int8 NULL,
- "result" oid NULL,
- status int4 NULL,
- wf_context oid NULL,
- wf_init_params oid NULL,
- wf_instance_id int8 NULL,
- workflow_id int8 NULL,
- CONSTRAINT pj_workflow_instance_info_pkey PRIMARY KEY (id),
- CONSTRAINT uidx01_wf_instance UNIQUE (wf_instance_id)
-);
-CREATE INDEX idx01_wf_instance ON pj_workflow_instance_info USING btree (workflow_id, status, app_id, expected_trigger_time);
-
-
--- pj_workflow_node_info definition
-
--- Drop table
-
--- DROP TABLE pj_workflow_node_info;
-
-CREATE TABLE pj_workflow_node_info (
- id int8 NOT NULL,
- app_id int8 NOT NULL,
- "enable" bool NOT NULL,
- extra oid NULL,
- gmt_create timestamp NOT NULL,
- gmt_modified timestamp NOT NULL,
- job_id int8 NULL,
- node_name varchar(255) NULL,
- node_params oid NULL,
- skip_when_failed bool NOT NULL,
- "type" int4 NULL,
- workflow_id int8 NULL,
- CONSTRAINT pj_workflow_node_info_pkey PRIMARY KEY (id)
-);
-CREATE INDEX idx01_workflow_node_info ON pj_workflow_node_info USING btree (workflow_id, gmt_create);
diff --git a/script/sql/postgres/snail_job_postgre.sql b/script/sql/postgres/snail_job_postgre.sql
new file mode 100644
index 0000000..30a871e
--- /dev/null
+++ b/script/sql/postgres/snail_job_postgre.sql
@@ -0,0 +1,825 @@
+/*
+ SnailJob Database Transfer Tool
+ Source Server Type : MySQL
+ Target Server Type : PostgreSQL
+ Date: 2024-05-13 22:49:34
+*/
+
+
+-- sj_namespace
+CREATE TABLE sj_namespace
+(
+ id bigserial PRIMARY KEY,
+ name varchar(64) NOT NULL,
+ unique_id varchar(64) NOT NULL,
+ description varchar(256) NOT NULL DEFAULT '',
+ deleted smallint NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_namespace_01 ON sj_namespace (name);
+
+COMMENT ON COLUMN sj_namespace.id IS '涓婚敭';
+COMMENT ON COLUMN sj_namespace.name IS '鍚嶇О';
+COMMENT ON COLUMN sj_namespace.unique_id IS '鍞竴id';
+COMMENT ON COLUMN sj_namespace.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_namespace.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_namespace.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_namespace.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_namespace IS '鍛藉悕绌洪棿';
+
+INSERT INTO sj_namespace VALUES (1, 'Development', 'dev', '', 0, now(), now());
+INSERT INTO sj_namespace VALUES (2, 'Production', 'prod', '', 0, now(), now());
+
+-- sj_group_config
+CREATE TABLE sj_group_config
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL DEFAULT '',
+ description varchar(256) NOT NULL DEFAULT '',
+ token varchar(64) NOT NULL DEFAULT 'SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT',
+ group_status smallint NOT NULL DEFAULT 0,
+ version int NOT NULL,
+ group_partition int NOT NULL,
+ id_generator_mode smallint NOT NULL DEFAULT 1,
+ init_scene smallint NOT NULL DEFAULT 0,
+ bucket_index int NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE UNIQUE INDEX uk_sj_group_config_01 ON sj_group_config (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_group_config.id IS '涓婚敭';
+COMMENT ON COLUMN sj_group_config.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_group_config.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_group_config.description IS '缁勬弿杩�';
+COMMENT ON COLUMN sj_group_config.token IS 'token';
+COMMENT ON COLUMN sj_group_config.group_status IS '缁勭姸鎬� 0銆佹湭鍚敤 1銆佸惎鐢�';
+COMMENT ON COLUMN sj_group_config.version IS '鐗堟湰鍙�';
+COMMENT ON COLUMN sj_group_config.group_partition IS '鍒嗗尯';
+COMMENT ON COLUMN sj_group_config.id_generator_mode IS '鍞竴id鐢熸垚妯″紡 榛樿鍙锋妯″紡';
+COMMENT ON COLUMN sj_group_config.init_scene IS '鏄惁鍒濆鍖栧満鏅� 0:鍚� 1:鏄�';
+COMMENT ON COLUMN sj_group_config.bucket_index IS 'bucket';
+COMMENT ON COLUMN sj_group_config.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_group_config.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_group_config IS '缁勯厤缃�';
+
+INSERT INTO sj_group_config VALUES (1, 'dev', 'ruoyi_group', '', 'SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT', 1, 1, 0, 1, 1, 4, now(), now());
+
+-- sj_notify_config
+CREATE TABLE sj_notify_config
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL,
+ business_id varchar(64) NOT NULL,
+ system_task_type smallint NOT NULL DEFAULT 3,
+ notify_status smallint NOT NULL DEFAULT 0,
+ recipient_ids varchar(128) NOT NULL,
+ notify_threshold int NOT NULL DEFAULT 0,
+ notify_scene smallint NOT NULL DEFAULT 0,
+ rate_limiter_status smallint NOT NULL DEFAULT 0,
+ rate_limiter_threshold int NOT NULL DEFAULT 0,
+ description varchar(256) NOT NULL DEFAULT '',
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_notify_config_01 ON sj_notify_config (namespace_id, group_name, business_id);
+
+COMMENT ON COLUMN sj_notify_config.id IS '涓婚敭';
+COMMENT ON COLUMN sj_notify_config.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_notify_config.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_notify_config.business_id IS '涓氬姟id ( job_id鎴杦orkflow_id鎴杝cene_name ) ';
+COMMENT ON COLUMN sj_notify_config.system_task_type IS '浠诲姟绫诲瀷 1. 閲嶈瘯浠诲姟 2. 閲嶈瘯鍥炶皟 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟';
+COMMENT ON COLUMN sj_notify_config.notify_status IS '閫氱煡鐘舵�� 0銆佹湭鍚敤 1銆佸惎鐢�';
+COMMENT ON COLUMN sj_notify_config.recipient_ids IS '鎺ユ敹浜篿d鍒楄〃';
+COMMENT ON COLUMN sj_notify_config.notify_threshold IS '閫氱煡闃堝��';
+COMMENT ON COLUMN sj_notify_config.notify_scene IS '閫氱煡鍦烘櫙';
+COMMENT ON COLUMN sj_notify_config.rate_limiter_status IS '闄愭祦鐘舵�� 0銆佹湭鍚敤 1銆佸惎鐢�';
+COMMENT ON COLUMN sj_notify_config.rate_limiter_threshold IS '姣忕闄愭祦闃堝��';
+COMMENT ON COLUMN sj_notify_config.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_notify_config.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_notify_config.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_notify_config IS '閫氱煡閰嶇疆';
+
+-- sj_notify_recipient
+CREATE TABLE sj_notify_recipient
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ recipient_name varchar(64) NOT NULL,
+ notify_type smallint NOT NULL DEFAULT 0,
+ notify_attribute varchar(512) NOT NULL,
+ description varchar(256) NOT NULL DEFAULT '',
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_notify_recipient_01 ON sj_notify_recipient (namespace_id);
+
+COMMENT ON COLUMN sj_notify_recipient.id IS '涓婚敭';
+COMMENT ON COLUMN sj_notify_recipient.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_notify_recipient.recipient_name IS '鎺ユ敹浜哄悕绉�';
+COMMENT ON COLUMN sj_notify_recipient.notify_type IS '閫氱煡绫诲瀷 1銆侀拤閽� 2銆侀偖浠� 3銆佷紒涓氬井淇� 4 椋炰功';
+COMMENT ON COLUMN sj_notify_recipient.notify_attribute IS '閰嶇疆灞炴��';
+COMMENT ON COLUMN sj_notify_recipient.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_notify_recipient.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_notify_recipient.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_notify_recipient IS '鍛婅閫氱煡鎺ユ敹浜�';
+
+-- sj_retry_dead_letter_0
+CREATE TABLE sj_retry_dead_letter_0
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ unique_id varchar(64) NOT NULL,
+ group_name varchar(64) NOT NULL,
+ scene_name varchar(64) NOT NULL,
+ idempotent_id varchar(64) NOT NULL,
+ biz_no varchar(64) NOT NULL DEFAULT '',
+ executor_name varchar(512) NOT NULL DEFAULT '',
+ args_str text NOT NULL,
+ ext_attrs text NOT NULL,
+ task_type smallint NOT NULL DEFAULT 1,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE UNIQUE INDEX uk_sj_retry_dead_letter_0_01 ON sj_retry_dead_letter_0 (namespace_id, group_name, unique_id);
+
+CREATE INDEX idx_sj_retry_dead_letter_0_01 ON sj_retry_dead_letter_0 (namespace_id, group_name, scene_name);
+CREATE INDEX idx_sj_retry_dead_letter_0_02 ON sj_retry_dead_letter_0 (idempotent_id);
+CREATE INDEX idx_sj_retry_dead_letter_0_03 ON sj_retry_dead_letter_0 (biz_no);
+CREATE INDEX idx_sj_retry_dead_letter_0_04 ON sj_retry_dead_letter_0 (create_dt);
+
+COMMENT ON COLUMN sj_retry_dead_letter_0.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_dead_letter_0.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_dead_letter_0.unique_id IS '鍚岀粍涓媔d鍞竴';
+COMMENT ON COLUMN sj_retry_dead_letter_0.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_dead_letter_0.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_dead_letter_0.idempotent_id IS '骞傜瓑id';
+COMMENT ON COLUMN sj_retry_dead_letter_0.biz_no IS '涓氬姟缂栧彿';
+COMMENT ON COLUMN sj_retry_dead_letter_0.executor_name IS '鎵ц鍣ㄥ悕绉�';
+COMMENT ON COLUMN sj_retry_dead_letter_0.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_retry_dead_letter_0.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_retry_dead_letter_0.task_type IS '浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�';
+COMMENT ON COLUMN sj_retry_dead_letter_0.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON TABLE sj_retry_dead_letter_0 IS '姝讳俊闃熷垪琛�';
+
+-- sj_retry_task_0
+CREATE TABLE sj_retry_task_0
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ unique_id varchar(64) NOT NULL,
+ group_name varchar(64) NOT NULL,
+ scene_name varchar(64) NOT NULL,
+ idempotent_id varchar(64) NOT NULL,
+ biz_no varchar(64) NOT NULL DEFAULT '',
+ executor_name varchar(512) NOT NULL DEFAULT '',
+ args_str text NOT NULL,
+ ext_attrs text NOT NULL,
+ next_trigger_at timestamp NOT NULL,
+ retry_count int NOT NULL DEFAULT 0,
+ retry_status smallint NOT NULL DEFAULT 0,
+ task_type smallint NOT NULL DEFAULT 1,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE UNIQUE INDEX uk_sj_retry_task_0_01 ON sj_retry_task_0 (namespace_id, group_name, unique_id);
+
+CREATE INDEX idx_sj_retry_task_0_01 ON sj_retry_task_0 (namespace_id, group_name, scene_name);
+CREATE INDEX idx_sj_retry_task_0_02 ON sj_retry_task_0 (namespace_id, group_name, task_type);
+CREATE INDEX idx_sj_retry_task_0_03 ON sj_retry_task_0 (namespace_id, group_name, retry_status);
+CREATE INDEX idx_sj_retry_task_0_04 ON sj_retry_task_0 (idempotent_id);
+CREATE INDEX idx_sj_retry_task_0_05 ON sj_retry_task_0 (biz_no);
+CREATE INDEX idx_sj_retry_task_0_06 ON sj_retry_task_0 (create_dt);
+
+COMMENT ON COLUMN sj_retry_task_0.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_task_0.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_task_0.unique_id IS '鍚岀粍涓媔d鍞竴';
+COMMENT ON COLUMN sj_retry_task_0.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_task_0.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_task_0.idempotent_id IS '骞傜瓑id';
+COMMENT ON COLUMN sj_retry_task_0.biz_no IS '涓氬姟缂栧彿';
+COMMENT ON COLUMN sj_retry_task_0.executor_name IS '鎵ц鍣ㄥ悕绉�';
+COMMENT ON COLUMN sj_retry_task_0.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_retry_task_0.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_retry_task_0.next_trigger_at IS '涓嬫瑙﹀彂鏃堕棿';
+COMMENT ON COLUMN sj_retry_task_0.retry_count IS '閲嶈瘯娆℃暟';
+COMMENT ON COLUMN sj_retry_task_0.retry_status IS '閲嶈瘯鐘舵�� 0銆侀噸璇曚腑 1銆佹垚鍔� 2銆佹渶澶ч噸璇曟鏁�';
+COMMENT ON COLUMN sj_retry_task_0.task_type IS '浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�';
+COMMENT ON COLUMN sj_retry_task_0.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_retry_task_0.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_retry_task_0 IS '浠诲姟琛�';
+
+-- sj_retry_task_log
+CREATE TABLE sj_retry_task_log
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ unique_id varchar(64) NOT NULL,
+ group_name varchar(64) NOT NULL,
+ scene_name varchar(64) NOT NULL,
+ idempotent_id varchar(64) NOT NULL,
+ biz_no varchar(64) NOT NULL DEFAULT '',
+ executor_name varchar(512) NOT NULL DEFAULT '',
+ args_str text NOT NULL,
+ ext_attrs text NOT NULL,
+ retry_status smallint NOT NULL DEFAULT 0,
+ task_type smallint NOT NULL DEFAULT 1,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_retry_task_log_01 ON sj_retry_task_log (namespace_id, group_name, scene_name);
+CREATE INDEX idx_sj_retry_task_log_02 ON sj_retry_task_log (retry_status);
+CREATE INDEX idx_sj_retry_task_log_03 ON sj_retry_task_log (idempotent_id);
+CREATE INDEX idx_sj_retry_task_log_04 ON sj_retry_task_log (unique_id);
+CREATE INDEX idx_sj_retry_task_log_05 ON sj_retry_task_log (biz_no);
+CREATE INDEX idx_sj_retry_task_log_06 ON sj_retry_task_log (create_dt);
+
+COMMENT ON COLUMN sj_retry_task_log.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_task_log.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_task_log.unique_id IS '鍚岀粍涓媔d鍞竴';
+COMMENT ON COLUMN sj_retry_task_log.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_task_log.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_task_log.idempotent_id IS '骞傜瓑id';
+COMMENT ON COLUMN sj_retry_task_log.biz_no IS '涓氬姟缂栧彿';
+COMMENT ON COLUMN sj_retry_task_log.executor_name IS '鎵ц鍣ㄥ悕绉�';
+COMMENT ON COLUMN sj_retry_task_log.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_retry_task_log.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_retry_task_log.retry_status IS '閲嶈瘯鐘舵�� 0銆侀噸璇曚腑 1銆佹垚鍔� 2銆佹渶澶ф鏁�';
+COMMENT ON COLUMN sj_retry_task_log.task_type IS '浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�';
+COMMENT ON COLUMN sj_retry_task_log.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_retry_task_log.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_retry_task_log IS '浠诲姟鏃ュ織鍩虹淇℃伅琛�';
+
+-- sj_retry_task_log_message
+CREATE TABLE sj_retry_task_log_message
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL,
+ unique_id varchar(64) NOT NULL,
+ message text NOT NULL,
+ log_num int NOT NULL DEFAULT 1,
+ real_time bigint NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_retry_task_log_message_01 ON sj_retry_task_log_message (namespace_id, group_name, unique_id);
+CREATE INDEX idx_sj_retry_task_log_message_02 ON sj_retry_task_log_message (create_dt);
+
+COMMENT ON COLUMN sj_retry_task_log_message.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_task_log_message.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_task_log_message.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_task_log_message.unique_id IS '鍚岀粍涓媔d鍞竴';
+COMMENT ON COLUMN sj_retry_task_log_message.message IS '寮傚父淇℃伅';
+COMMENT ON COLUMN sj_retry_task_log_message.log_num IS '鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_task_log_message.real_time IS '涓婃姤鏃堕棿';
+COMMENT ON COLUMN sj_retry_task_log_message.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON TABLE sj_retry_task_log_message IS '浠诲姟璋冨害鏃ュ織淇℃伅璁板綍琛�';
+
+-- sj_retry_scene_config
+CREATE TABLE sj_retry_scene_config
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ scene_name varchar(64) NOT NULL,
+ group_name varchar(64) NOT NULL,
+ scene_status smallint NOT NULL DEFAULT 0,
+ max_retry_count int NOT NULL DEFAULT 5,
+ back_off smallint NOT NULL DEFAULT 1,
+ trigger_interval varchar(16) NOT NULL DEFAULT '',
+ deadline_request bigint NOT NULL DEFAULT 60000,
+ executor_timeout int NOT NULL DEFAULT 5,
+ route_key smallint NOT NULL DEFAULT 4,
+ description varchar(256) NOT NULL DEFAULT '',
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE UNIQUE INDEX uk_sj_retry_scene_config_01 ON sj_retry_scene_config (namespace_id, group_name, scene_name);
+
+COMMENT ON COLUMN sj_retry_scene_config.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_scene_config.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_scene_config.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_scene_config.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_scene_config.scene_status IS '缁勭姸鎬� 0銆佹湭鍚敤 1銆佸惎鐢�';
+COMMENT ON COLUMN sj_retry_scene_config.max_retry_count IS '鏈�澶ч噸璇曟鏁�';
+COMMENT ON COLUMN sj_retry_scene_config.back_off IS '1銆侀粯璁ょ瓑绾� 2銆佸浐瀹氶棿闅旀椂闂� 3銆丆RON 琛ㄨ揪寮�';
+COMMENT ON COLUMN sj_retry_scene_config.trigger_interval IS '闂撮殧鏃堕暱';
+COMMENT ON COLUMN sj_retry_scene_config.deadline_request IS 'Deadline Request 璋冪敤閾捐秴鏃� 鍗曚綅姣';
+COMMENT ON COLUMN sj_retry_scene_config.executor_timeout IS '浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇';
+COMMENT ON COLUMN sj_retry_scene_config.route_key IS '璺敱绛栫暐';
+COMMENT ON COLUMN sj_retry_scene_config.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_retry_scene_config.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_retry_scene_config.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_retry_scene_config IS '鍦烘櫙閰嶇疆';
+
+-- sj_server_node
+CREATE TABLE sj_server_node
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL,
+ host_id varchar(64) NOT NULL,
+ host_ip varchar(64) NOT NULL,
+ host_port int NOT NULL,
+ expire_at timestamp NOT NULL,
+ node_type smallint NOT NULL,
+ ext_attrs varchar(256) NULL DEFAULT '',
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE UNIQUE INDEX uk_sj_server_node_01 ON sj_server_node (host_id, host_ip);
+
+CREATE INDEX idx_sj_server_node_01 ON sj_server_node (namespace_id, group_name);
+CREATE INDEX idx_sj_server_node_02 ON sj_server_node (expire_at, node_type);
+
+COMMENT ON COLUMN sj_server_node.id IS '涓婚敭';
+COMMENT ON COLUMN sj_server_node.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_server_node.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_server_node.host_id IS '涓绘満id';
+COMMENT ON COLUMN sj_server_node.host_ip IS '鏈哄櫒ip';
+COMMENT ON COLUMN sj_server_node.host_port IS '鏈哄櫒绔彛';
+COMMENT ON COLUMN sj_server_node.expire_at IS '杩囨湡鏃堕棿';
+COMMENT ON COLUMN sj_server_node.node_type IS '鑺傜偣绫诲瀷 1銆佸鎴风 2銆佹槸鏈嶅姟绔�';
+COMMENT ON COLUMN sj_server_node.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_server_node.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_server_node.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_server_node IS '鏈嶅姟鍣ㄨ妭鐐�';
+
+-- sj_distributed_lock
+CREATE TABLE sj_distributed_lock
+(
+ id bigserial PRIMARY KEY,
+ name varchar(64) NOT NULL,
+ lock_until timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ locked_at timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3),
+ locked_by varchar(255) NOT NULL,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+COMMENT ON COLUMN sj_distributed_lock.id IS '涓婚敭';
+COMMENT ON COLUMN sj_distributed_lock.name IS '閿佸悕绉�';
+COMMENT ON COLUMN sj_distributed_lock.lock_until IS '閿佸畾鏃堕暱';
+COMMENT ON COLUMN sj_distributed_lock.locked_at IS '閿佸畾鏃堕棿';
+COMMENT ON COLUMN sj_distributed_lock.locked_by IS '閿佸畾鑰�';
+COMMENT ON COLUMN sj_distributed_lock.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_distributed_lock.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_distributed_lock IS '閿佸畾琛�';
+
+-- sj_system_user
+CREATE TABLE sj_system_user
+(
+ id bigserial PRIMARY KEY,
+ username varchar(64) NOT NULL,
+ password varchar(128) NOT NULL,
+ role smallint NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+COMMENT ON COLUMN sj_system_user.id IS '涓婚敭';
+COMMENT ON COLUMN sj_system_user.username IS '璐﹀彿';
+COMMENT ON COLUMN sj_system_user.password IS '瀵嗙爜';
+COMMENT ON COLUMN sj_system_user.role IS '瑙掕壊锛�1-鏅�氱敤鎴枫��2-绠$悊鍛�';
+COMMENT ON COLUMN sj_system_user.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_system_user.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_system_user IS '绯荤粺鐢ㄦ埛琛�';
+
+-- pwd: admin
+INSERT INTO sj_system_user VALUES (1, 'admin', '465c194afb65670f38322df087f0a9bb225cc257e43eb4ac5a0c98ef5b3173ac', 2, now(), now());
+
+-- sj_system_user_permission
+CREATE TABLE sj_system_user_permission
+(
+ id bigserial PRIMARY KEY,
+ group_name varchar(64) NOT NULL,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ system_user_id bigint NOT NULL,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE UNIQUE INDEX uk_sj_system_user_permission_01 ON sj_system_user_permission (namespace_id, group_name, system_user_id);
+
+COMMENT ON COLUMN sj_system_user_permission.id IS '涓婚敭';
+COMMENT ON COLUMN sj_system_user_permission.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_system_user_permission.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_system_user_permission.system_user_id IS '绯荤粺鐢ㄦ埛id';
+COMMENT ON COLUMN sj_system_user_permission.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_system_user_permission.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_system_user_permission IS '绯荤粺鐢ㄦ埛鏉冮檺琛�';
+
+-- sj_sequence_alloc
+CREATE TABLE sj_sequence_alloc
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL DEFAULT '',
+ max_id bigint NOT NULL DEFAULT 1,
+ step int NOT NULL DEFAULT 100,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE UNIQUE INDEX uk_sj_sequence_alloc_01 ON sj_sequence_alloc (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_sequence_alloc.id IS '涓婚敭';
+COMMENT ON COLUMN sj_sequence_alloc.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_sequence_alloc.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_sequence_alloc.max_id IS '鏈�澶d';
+COMMENT ON COLUMN sj_sequence_alloc.step IS '姝ラ暱';
+COMMENT ON COLUMN sj_sequence_alloc.update_dt IS '鏇存柊鏃堕棿';
+COMMENT ON TABLE sj_sequence_alloc IS '鍙锋妯″紡搴忓彿ID鍒嗛厤琛�';
+
+-- sj_job
+CREATE TABLE sj_job
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL,
+ job_name varchar(64) NOT NULL,
+ args_str text NULL DEFAULT NULL,
+ args_type smallint NOT NULL DEFAULT 1,
+ next_trigger_at bigint NOT NULL,
+ job_status smallint NOT NULL DEFAULT 1,
+ task_type smallint NOT NULL DEFAULT 1,
+ route_key smallint NOT NULL DEFAULT 4,
+ executor_type smallint NOT NULL DEFAULT 1,
+ executor_info varchar(255) NULL DEFAULT NULL,
+ trigger_type smallint NOT NULL,
+ trigger_interval varchar(255) NOT NULL,
+ block_strategy smallint NOT NULL DEFAULT 1,
+ executor_timeout int NOT NULL DEFAULT 0,
+ max_retry_times int NOT NULL DEFAULT 0,
+ parallel_num int NOT NULL DEFAULT 1,
+ retry_interval int NOT NULL DEFAULT 0,
+ bucket_index int NOT NULL DEFAULT 0,
+ resident smallint NOT NULL DEFAULT 0,
+ description varchar(256) NOT NULL DEFAULT '',
+ ext_attrs varchar(256) NULL DEFAULT '',
+ deleted smallint NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_job_01 ON sj_job (namespace_id, group_name);
+CREATE INDEX idx_sj_job_02 ON sj_job (job_status, bucket_index);
+CREATE INDEX idx_sj_job_03 ON sj_job (create_dt);
+
+COMMENT ON COLUMN sj_job.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job.job_name IS '鍚嶇О';
+COMMENT ON COLUMN sj_job.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_job.args_type IS '鍙傛暟绫诲瀷 ';
+COMMENT ON COLUMN sj_job.next_trigger_at IS '涓嬫瑙﹀彂鏃堕棿';
+COMMENT ON COLUMN sj_job.job_status IS '浠诲姟鐘舵�� 0銆佸叧闂��1銆佸紑鍚�';
+COMMENT ON COLUMN sj_job.task_type IS '浠诲姟绫诲瀷 1銆侀泦缇� 2銆佸箍鎾� 3銆佸垏鐗�';
+COMMENT ON COLUMN sj_job.route_key IS '璺敱绛栫暐';
+COMMENT ON COLUMN sj_job.executor_type IS '鎵ц鍣ㄧ被鍨�';
+COMMENT ON COLUMN sj_job.executor_info IS '鎵ц鍣ㄥ悕绉�';
+COMMENT ON COLUMN sj_job.trigger_type IS '瑙﹀彂绫诲瀷 1.CRON 琛ㄨ揪寮� 2. 鍥哄畾鏃堕棿';
+COMMENT ON COLUMN sj_job.trigger_interval IS '闂撮殧鏃堕暱';
+COMMENT ON COLUMN sj_job.block_strategy IS '闃诲绛栫暐 1銆佷涪寮� 2銆佽鐩� 3銆佸苟琛�';
+COMMENT ON COLUMN sj_job.executor_timeout IS '浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇';
+COMMENT ON COLUMN sj_job.max_retry_times IS '鏈�澶ч噸璇曟鏁�';
+COMMENT ON COLUMN sj_job.parallel_num IS '骞惰鏁�';
+COMMENT ON COLUMN sj_job.retry_interval IS '閲嶈瘯闂撮殧 ( s ) ';
+COMMENT ON COLUMN sj_job.bucket_index IS 'bucket';
+COMMENT ON COLUMN sj_job.resident IS '鏄惁鏄父椹讳换鍔�';
+COMMENT ON COLUMN sj_job.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_job.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_job.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_job.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_job.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_job IS '浠诲姟淇℃伅';
+
+INSERT INTO sj_job VALUES (1, 'dev', 'ruoyi_group', 'demo-job', null, 1, 1710344035622, 1, 1, 4, 1, 'testJobExecutor', 2, '60', 1, 60, 3, 1, 1, 116, 0, '', '', 0, now(), now());
+
+-- sj_job_log_message
+CREATE TABLE sj_job_log_message
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL,
+ job_id bigint NOT NULL,
+ task_batch_id bigint NOT NULL,
+ task_id bigint NOT NULL,
+ message text NOT NULL,
+ log_num int NOT NULL DEFAULT 1,
+ real_time bigint NOT NULL DEFAULT 0,
+ ext_attrs varchar(256) NULL DEFAULT '',
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_job_log_message_01 ON sj_job_log_message (task_batch_id, task_id);
+CREATE INDEX idx_sj_job_log_message_02 ON sj_job_log_message (create_dt);
+CREATE INDEX idx_sj_job_log_message_03 ON sj_job_log_message (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_job_log_message.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job_log_message.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job_log_message.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job_log_message.job_id IS '浠诲姟淇℃伅id';
+COMMENT ON COLUMN sj_job_log_message.task_batch_id IS '浠诲姟鎵规id';
+COMMENT ON COLUMN sj_job_log_message.task_id IS '璋冨害浠诲姟id';
+COMMENT ON COLUMN sj_job_log_message.message IS '璋冨害淇℃伅';
+COMMENT ON COLUMN sj_job_log_message.log_num IS '鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_log_message.real_time IS '涓婃姤鏃堕棿';
+COMMENT ON COLUMN sj_job_log_message.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_job_log_message.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON TABLE sj_job_log_message IS '璋冨害鏃ュ織';
+
+-- sj_job_task
+CREATE TABLE sj_job_task
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL,
+ job_id bigint NOT NULL,
+ task_batch_id bigint NOT NULL,
+ parent_id bigint NOT NULL DEFAULT 0,
+ task_status smallint NOT NULL DEFAULT 0,
+ retry_count int NOT NULL DEFAULT 0,
+ client_info varchar(128) NULL DEFAULT NULL,
+ result_message text NOT NULL,
+ args_str text NULL DEFAULT NULL,
+ args_type smallint NOT NULL DEFAULT 1,
+ ext_attrs varchar(256) NULL DEFAULT '',
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_job_task_01 ON sj_job_task (task_batch_id, task_status);
+CREATE INDEX idx_sj_job_task_02 ON sj_job_task (create_dt);
+CREATE INDEX idx_sj_job_task_03 ON sj_job_task (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_job_task.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job_task.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job_task.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job_task.job_id IS '浠诲姟淇℃伅id';
+COMMENT ON COLUMN sj_job_task.task_batch_id IS '璋冨害浠诲姟id';
+COMMENT ON COLUMN sj_job_task.parent_id IS '鐖舵墽琛屽櫒id';
+COMMENT ON COLUMN sj_job_task.task_status IS '鎵ц鐨勭姸鎬� 0銆佸け璐� 1銆佹垚鍔�';
+COMMENT ON COLUMN sj_job_task.retry_count IS '閲嶈瘯娆℃暟';
+COMMENT ON COLUMN sj_job_task.client_info IS '瀹㈡埛绔湴鍧� clientId#ip:port';
+COMMENT ON COLUMN sj_job_task.result_message IS '鎵ц缁撴灉';
+COMMENT ON COLUMN sj_job_task.args_str IS '鎵ц鏂规硶鍙傛暟';
+COMMENT ON COLUMN sj_job_task.args_type IS '鍙傛暟绫诲瀷 ';
+COMMENT ON COLUMN sj_job_task.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_job_task.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_job_task.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_job_task IS '浠诲姟瀹炰緥';
+
+-- sj_job_task_batch
+CREATE TABLE sj_job_task_batch
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL,
+ job_id bigint NOT NULL,
+ workflow_node_id bigint NOT NULL DEFAULT 0,
+ parent_workflow_node_id bigint NOT NULL DEFAULT 0,
+ workflow_task_batch_id bigint NOT NULL DEFAULT 0,
+ task_batch_status smallint NOT NULL DEFAULT 0,
+ operation_reason smallint NOT NULL DEFAULT 0,
+ execution_at bigint NOT NULL DEFAULT 0,
+ system_task_type smallint NOT NULL DEFAULT 3,
+ parent_id varchar(64) NOT NULL DEFAULT '',
+ ext_attrs varchar(256) NULL DEFAULT '',
+ deleted smallint NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_job_task_batch_01 ON sj_job_task_batch (job_id, task_batch_status);
+CREATE INDEX idx_sj_job_task_batch_02 ON sj_job_task_batch (create_dt);
+CREATE INDEX idx_sj_job_task_batch_03 ON sj_job_task_batch (namespace_id, group_name);
+CREATE INDEX idx_sj_job_task_batch_04 ON sj_job_task_batch (workflow_task_batch_id, workflow_node_id);
+
+COMMENT ON COLUMN sj_job_task_batch.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job_task_batch.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job_task_batch.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job_task_batch.job_id IS '浠诲姟id';
+COMMENT ON COLUMN sj_job_task_batch.workflow_node_id IS '宸ヤ綔娴佽妭鐐筰d';
+COMMENT ON COLUMN sj_job_task_batch.parent_workflow_node_id IS '宸ヤ綔娴佷换鍔$埗鎵规id';
+COMMENT ON COLUMN sj_job_task_batch.workflow_task_batch_id IS '宸ヤ綔娴佷换鍔℃壒娆d';
+COMMENT ON COLUMN sj_job_task_batch.task_batch_status IS '浠诲姟鎵规鐘舵�� 0銆佸け璐� 1銆佹垚鍔�';
+COMMENT ON COLUMN sj_job_task_batch.operation_reason IS '鎿嶄綔鍘熷洜';
+COMMENT ON COLUMN sj_job_task_batch.execution_at IS '浠诲姟鎵ц鏃堕棿';
+COMMENT ON COLUMN sj_job_task_batch.system_task_type IS '浠诲姟绫诲瀷 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟';
+COMMENT ON COLUMN sj_job_task_batch.parent_id IS '鐖惰妭鐐�';
+COMMENT ON COLUMN sj_job_task_batch.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_job_task_batch.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_job_task_batch.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_job_task_batch.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_job_task_batch IS '浠诲姟鎵规';
+
+-- sj_job_summary
+CREATE TABLE sj_job_summary
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL DEFAULT '',
+ business_id bigint NOT NULL,
+ system_task_type smallint NOT NULL DEFAULT 3,
+ trigger_at timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ success_num int NOT NULL DEFAULT 0,
+ fail_num int NOT NULL DEFAULT 0,
+ fail_reason varchar(512) NOT NULL DEFAULT '',
+ stop_num int NOT NULL DEFAULT 0,
+ stop_reason varchar(512) NOT NULL DEFAULT '',
+ cancel_num int NOT NULL DEFAULT 0,
+ cancel_reason varchar(512) NOT NULL DEFAULT '',
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE UNIQUE INDEX uk_sj_job_summary_01 ON sj_job_summary (trigger_at, system_task_type, business_id);
+
+CREATE INDEX idx_sj_job_summary_01 ON sj_job_summary (namespace_id, group_name, business_id);
+
+COMMENT ON COLUMN sj_job_summary.id IS '涓婚敭';
+COMMENT ON COLUMN sj_job_summary.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_job_summary.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_job_summary.business_id IS '涓氬姟id ( job_id鎴杦orkflow_id ) ';
+COMMENT ON COLUMN sj_job_summary.system_task_type IS '浠诲姟绫诲瀷 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟';
+COMMENT ON COLUMN sj_job_summary.trigger_at IS '缁熻鏃堕棿';
+COMMENT ON COLUMN sj_job_summary.success_num IS '鎵ц鎴愬姛-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_summary.fail_num IS '鎵ц澶辫触-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_summary.fail_reason IS '澶辫触鍘熷洜';
+COMMENT ON COLUMN sj_job_summary.stop_num IS '鎵ц澶辫触-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_summary.stop_reason IS '澶辫触鍘熷洜';
+COMMENT ON COLUMN sj_job_summary.cancel_num IS '鎵ц澶辫触-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_job_summary.cancel_reason IS '澶辫触鍘熷洜';
+COMMENT ON COLUMN sj_job_summary.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_job_summary.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_job_summary IS 'DashBoard_Job';
+
+-- sj_retry_summary
+CREATE TABLE sj_retry_summary
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL DEFAULT '',
+ scene_name varchar(50) NOT NULL DEFAULT '',
+ trigger_at timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ running_num int NOT NULL DEFAULT 0,
+ finish_num int NOT NULL DEFAULT 0,
+ max_count_num int NOT NULL DEFAULT 0,
+ suspend_num int NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE UNIQUE INDEX uk_sj_retry_summary_01 ON sj_retry_summary (namespace_id, group_name, scene_name, trigger_at);
+
+CREATE INDEX idx_sj_retry_summary_01 ON sj_retry_summary (trigger_at);
+
+COMMENT ON COLUMN sj_retry_summary.id IS '涓婚敭';
+COMMENT ON COLUMN sj_retry_summary.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_retry_summary.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_retry_summary.scene_name IS '鍦烘櫙鍚嶇О';
+COMMENT ON COLUMN sj_retry_summary.trigger_at IS '缁熻鏃堕棿';
+COMMENT ON COLUMN sj_retry_summary.running_num IS '閲嶈瘯涓�-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_summary.finish_num IS '閲嶈瘯瀹屾垚-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_summary.max_count_num IS '閲嶈瘯鍒拌揪鏈�澶ф鏁�-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_summary.suspend_num IS '鏆傚仠閲嶈瘯-鏃ュ織鏁伴噺';
+COMMENT ON COLUMN sj_retry_summary.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_retry_summary.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_retry_summary IS 'DashBoard_Retry';
+
+-- sj_workflow
+CREATE TABLE sj_workflow
+(
+ id bigserial PRIMARY KEY,
+ workflow_name varchar(64) NOT NULL,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL,
+ workflow_status smallint NOT NULL DEFAULT 1,
+ trigger_type smallint NOT NULL,
+ trigger_interval varchar(255) NOT NULL,
+ next_trigger_at bigint NOT NULL,
+ block_strategy smallint NOT NULL DEFAULT 1,
+ executor_timeout int NOT NULL DEFAULT 0,
+ description varchar(256) NOT NULL DEFAULT '',
+ flow_info text NULL DEFAULT NULL,
+ bucket_index int NOT NULL DEFAULT 0,
+ version int NOT NULL,
+ ext_attrs varchar(256) NULL DEFAULT '',
+ deleted smallint NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_workflow_01 ON sj_workflow (create_dt);
+CREATE INDEX idx_sj_workflow_02 ON sj_workflow (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_workflow.id IS '涓婚敭';
+COMMENT ON COLUMN sj_workflow.workflow_name IS '宸ヤ綔娴佸悕绉�';
+COMMENT ON COLUMN sj_workflow.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_workflow.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_workflow.workflow_status IS '宸ヤ綔娴佺姸鎬� 0銆佸叧闂��1銆佸紑鍚�';
+COMMENT ON COLUMN sj_workflow.trigger_type IS '瑙﹀彂绫诲瀷 1.CRON 琛ㄨ揪寮� 2. 鍥哄畾鏃堕棿';
+COMMENT ON COLUMN sj_workflow.trigger_interval IS '闂撮殧鏃堕暱';
+COMMENT ON COLUMN sj_workflow.next_trigger_at IS '涓嬫瑙﹀彂鏃堕棿';
+COMMENT ON COLUMN sj_workflow.block_strategy IS '闃诲绛栫暐 1銆佷涪寮� 2銆佽鐩� 3銆佸苟琛�';
+COMMENT ON COLUMN sj_workflow.executor_timeout IS '浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇';
+COMMENT ON COLUMN sj_workflow.description IS '鎻忚堪';
+COMMENT ON COLUMN sj_workflow.flow_info IS '娴佺▼淇℃伅';
+COMMENT ON COLUMN sj_workflow.bucket_index IS 'bucket';
+COMMENT ON COLUMN sj_workflow.version IS '鐗堟湰鍙�';
+COMMENT ON COLUMN sj_workflow.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_workflow.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_workflow.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_workflow.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_workflow IS '宸ヤ綔娴�';
+
+-- sj_workflow_node
+CREATE TABLE sj_workflow_node
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ node_name varchar(64) NOT NULL,
+ group_name varchar(64) NOT NULL,
+ job_id bigint NOT NULL,
+ workflow_id bigint NOT NULL,
+ node_type smallint NOT NULL DEFAULT 1,
+ expression_type smallint NOT NULL DEFAULT 0,
+ fail_strategy smallint NOT NULL DEFAULT 1,
+ workflow_node_status smallint NOT NULL DEFAULT 1,
+ priority_level int NOT NULL DEFAULT 1,
+ node_info text NULL DEFAULT NULL,
+ version int NOT NULL,
+ ext_attrs varchar(256) NULL DEFAULT '',
+ deleted smallint NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_workflow_node_01 ON sj_workflow_node (create_dt);
+CREATE INDEX idx_sj_workflow_node_02 ON sj_workflow_node (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_workflow_node.id IS '涓婚敭';
+COMMENT ON COLUMN sj_workflow_node.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_workflow_node.node_name IS '鑺傜偣鍚嶇О';
+COMMENT ON COLUMN sj_workflow_node.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_workflow_node.job_id IS '浠诲姟淇℃伅id';
+COMMENT ON COLUMN sj_workflow_node.workflow_id IS '宸ヤ綔娴両D';
+COMMENT ON COLUMN sj_workflow_node.node_type IS '1銆佷换鍔¤妭鐐� 2銆佹潯浠惰妭鐐�';
+COMMENT ON COLUMN sj_workflow_node.expression_type IS '1銆丼pEl銆�2銆丄viator 3銆丵L';
+COMMENT ON COLUMN sj_workflow_node.fail_strategy IS '澶辫触绛栫暐 1銆佽烦杩� 2銆侀樆濉�';
+COMMENT ON COLUMN sj_workflow_node.workflow_node_status IS '宸ヤ綔娴佽妭鐐圭姸鎬� 0銆佸叧闂��1銆佸紑鍚�';
+COMMENT ON COLUMN sj_workflow_node.priority_level IS '浼樺厛绾�';
+COMMENT ON COLUMN sj_workflow_node.node_info IS '鑺傜偣淇℃伅 ';
+COMMENT ON COLUMN sj_workflow_node.version IS '鐗堟湰鍙�';
+COMMENT ON COLUMN sj_workflow_node.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_workflow_node.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_workflow_node.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_workflow_node.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_workflow_node IS '宸ヤ綔娴佽妭鐐�';
+
+-- sj_workflow_task_batch
+CREATE TABLE sj_workflow_task_batch
+(
+ id bigserial PRIMARY KEY,
+ namespace_id varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name varchar(64) NOT NULL,
+ workflow_id bigint NOT NULL,
+ task_batch_status smallint NOT NULL DEFAULT 0,
+ operation_reason smallint NOT NULL DEFAULT 0,
+ flow_info text NULL DEFAULT NULL,
+ execution_at bigint NOT NULL DEFAULT 0,
+ ext_attrs varchar(256) NULL DEFAULT '',
+ deleted smallint NOT NULL DEFAULT 0,
+ create_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE INDEX idx_sj_workflow_task_batch_01 ON sj_workflow_task_batch (workflow_id, task_batch_status);
+CREATE INDEX idx_sj_workflow_task_batch_02 ON sj_workflow_task_batch (create_dt);
+CREATE INDEX idx_sj_workflow_task_batch_03 ON sj_workflow_task_batch (namespace_id, group_name);
+
+COMMENT ON COLUMN sj_workflow_task_batch.id IS '涓婚敭';
+COMMENT ON COLUMN sj_workflow_task_batch.namespace_id IS '鍛藉悕绌洪棿id';
+COMMENT ON COLUMN sj_workflow_task_batch.group_name IS '缁勫悕绉�';
+COMMENT ON COLUMN sj_workflow_task_batch.workflow_id IS '宸ヤ綔娴佷换鍔d';
+COMMENT ON COLUMN sj_workflow_task_batch.task_batch_status IS '浠诲姟鎵规鐘舵�� 0銆佸け璐� 1銆佹垚鍔�';
+COMMENT ON COLUMN sj_workflow_task_batch.operation_reason IS '鎿嶄綔鍘熷洜';
+COMMENT ON COLUMN sj_workflow_task_batch.flow_info IS '娴佺▼淇℃伅';
+COMMENT ON COLUMN sj_workflow_task_batch.execution_at IS '浠诲姟鎵ц鏃堕棿';
+COMMENT ON COLUMN sj_workflow_task_batch.ext_attrs IS '鎵╁睍瀛楁';
+COMMENT ON COLUMN sj_workflow_task_batch.deleted IS '閫昏緫鍒犻櫎 1銆佸垹闄�';
+COMMENT ON COLUMN sj_workflow_task_batch.create_dt IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN sj_workflow_task_batch.update_dt IS '淇敼鏃堕棿';
+COMMENT ON TABLE sj_workflow_task_batch IS '宸ヤ綔娴佹壒娆�';
+
diff --git a/script/sql/powerjob.sql b/script/sql/powerjob.sql
deleted file mode 100644
index 9381b88..0000000
--- a/script/sql/powerjob.sql
+++ /dev/null
@@ -1,233 +0,0 @@
--- ----------------------------
--- Table structure for pj_app_info
--- ----------------------------
-DROP TABLE IF EXISTS `pj_app_info`;
-CREATE TABLE `pj_app_info` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `app_name` varchar(255) NULL DEFAULT NULL,
- `current_server` varchar(255) NULL DEFAULT NULL,
- `gmt_create` datetime(6) NULL DEFAULT NULL,
- `gmt_modified` datetime(6) NULL DEFAULT NULL,
- `password` varchar(255) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- UNIQUE INDEX `uidx01_app_info`(`app_name`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 2 ROW_FORMAT = Dynamic;
-
--- ----------------------------
--- Records of pj_app_info
--- ----------------------------
-INSERT INTO `pj_app_info` VALUES (1, 'ruoyi-worker', '127.0.0.1:10010', '2023-06-13 16:32:59.263000', '2023-07-04 17:25:49.798000', '123456');
-
--- ----------------------------
--- Table structure for pj_container_info
--- ----------------------------
-DROP TABLE IF EXISTS `pj_container_info`;
-CREATE TABLE `pj_container_info` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `app_id` bigint(0) NULL DEFAULT NULL,
- `container_name` varchar(255) NULL DEFAULT NULL,
- `gmt_create` datetime(6) NULL DEFAULT NULL,
- `gmt_modified` datetime(6) NULL DEFAULT NULL,
- `last_deploy_time` datetime(6) NULL DEFAULT NULL,
- `source_info` varchar(255) NULL DEFAULT NULL,
- `source_type` int(0) NULL DEFAULT NULL,
- `status` int(0) NULL DEFAULT NULL,
- `version` varchar(255) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- INDEX `idx01_container_info`(`app_id`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 1 ROW_FORMAT = Dynamic;
-
--- ----------------------------
--- Table structure for pj_instance_info
--- ----------------------------
-DROP TABLE IF EXISTS `pj_instance_info`;
-CREATE TABLE `pj_instance_info` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `actual_trigger_time` bigint(0) NULL DEFAULT NULL,
- `app_id` bigint(0) NULL DEFAULT NULL,
- `expected_trigger_time` bigint(0) NULL DEFAULT NULL,
- `finished_time` bigint(0) NULL DEFAULT NULL,
- `gmt_create` datetime(6) NULL DEFAULT NULL,
- `gmt_modified` datetime(6) NULL DEFAULT NULL,
- `instance_id` bigint(0) NULL DEFAULT NULL,
- `instance_params` longtext NULL,
- `job_id` bigint(0) NULL DEFAULT NULL,
- `job_params` longtext NULL,
- `last_report_time` bigint(0) NULL DEFAULT NULL,
- `result` longtext NULL,
- `running_times` bigint(0) NULL DEFAULT NULL,
- `status` int(0) NULL DEFAULT NULL,
- `task_tracker_address` varchar(255) NULL DEFAULT NULL,
- `type` int(0) NULL DEFAULT NULL,
- `wf_instance_id` bigint(0) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- INDEX `idx01_instance_info`(`job_id`, `status`) USING BTREE,
- INDEX `idx02_instance_info`(`app_id`, `status`) USING BTREE,
- INDEX `idx03_instance_info`(`instance_id`, `status`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 4 ROW_FORMAT = Dynamic;
-
--- ----------------------------
--- Table structure for pj_job_info
--- ----------------------------
-DROP TABLE IF EXISTS `pj_job_info`;
-CREATE TABLE `pj_job_info` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `alarm_config` varchar(255) NULL DEFAULT NULL,
- `app_id` bigint(0) NULL DEFAULT NULL,
- `concurrency` int(0) NULL DEFAULT NULL,
- `designated_workers` varchar(255) NULL DEFAULT NULL,
- `dispatch_strategy` int(0) NULL DEFAULT NULL,
- `execute_type` int(0) NULL DEFAULT NULL,
- `extra` varchar(255) NULL DEFAULT NULL,
- `gmt_create` datetime(6) NULL DEFAULT NULL,
- `gmt_modified` datetime(6) NULL DEFAULT NULL,
- `instance_retry_num` int(0) NULL DEFAULT NULL,
- `instance_time_limit` bigint(0) NULL DEFAULT NULL,
- `job_description` varchar(255) NULL DEFAULT NULL,
- `job_name` varchar(255) NULL DEFAULT NULL,
- `job_params` longtext NULL,
- `lifecycle` varchar(255) NULL DEFAULT NULL,
- `log_config` varchar(255) NULL DEFAULT NULL,
- `max_instance_num` int(0) NULL DEFAULT NULL,
- `max_worker_count` int(0) NULL DEFAULT NULL,
- `min_cpu_cores` double NOT NULL,
- `min_disk_space` double NOT NULL,
- `min_memory_space` double NOT NULL,
- `next_trigger_time` bigint(0) NULL DEFAULT NULL,
- `notify_user_ids` varchar(255) NULL DEFAULT NULL,
- `processor_info` varchar(255) NULL DEFAULT NULL,
- `processor_type` int(0) NULL DEFAULT NULL,
- `status` int(0) NULL DEFAULT NULL,
- `tag` varchar(255) NULL DEFAULT NULL,
- `task_retry_num` int(0) NULL DEFAULT NULL,
- `time_expression` varchar(255) NULL DEFAULT NULL,
- `time_expression_type` int(0) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- INDEX `idx01_job_info`(`app_id`, `status`, `time_expression_type`, `next_trigger_time`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 5 ROW_FORMAT = Dynamic;
-
--- ----------------------------
--- Records of pj_job_info
--- ----------------------------
-INSERT INTO `pj_job_info` VALUES (1, '{\"alertThreshold\":0,\"silenceWindowLen\":0,\"statisticWindowLen\":0}', 1, 5, '', 2, 1, NULL, '2023-06-02 15:01:27.717000', '2023-07-04 17:22:12.374000', 1, 0, '', '鍗曟満澶勭悊鍣ㄦ墽琛屾祴璇�', NULL, '{}', '{\"type\":1}', 0, 0, 0, 0, 0, NULL, NULL, 'org.dromara.job.processors.StandaloneProcessorDemo', 1, 2, NULL, 1, '30000', 3);
-INSERT INTO `pj_job_info` VALUES (2, '{\"alertThreshold\":0,\"silenceWindowLen\":0,\"statisticWindowLen\":0}', 1, 5, '', 1, 2, NULL, '2023-06-02 15:04:45.342000', '2023-07-04 17:22:12.816000', 0, 0, NULL, '骞挎挱澶勭悊鍣ㄦ祴璇�', NULL, '{}', '{\"type\":1}', 0, 0, 0, 0, 0, NULL, NULL, 'org.dromara.job.processors.BroadcastProcessorDemo', 1, 2, NULL, 1, '30000', 3);
-INSERT INTO `pj_job_info` VALUES (3, '{\"alertThreshold\":0,\"silenceWindowLen\":0,\"statisticWindowLen\":0}', 1, 5, '', 1, 4, NULL, '2023-06-02 15:13:23.519000', '2023-06-02 16:03:22.421000', 0, 0, NULL, 'Map澶勭悊鍣ㄦ祴璇�', NULL, '{}', '{\"type\":1}', 0, 0, 0, 0, 0, NULL, NULL, 'org.dromara.job.processors.MapProcessorDemo', 1, 2, NULL, 1, '1000', 3);
-INSERT INTO `pj_job_info` VALUES (4, '{\"alertThreshold\":0,\"silenceWindowLen\":0,\"statisticWindowLen\":0}', 1, 5, '', 1, 3, NULL, '2023-06-02 15:45:25.896000', '2023-06-02 16:03:23.125000', 0, 0, NULL, 'MapReduce澶勭悊鍣ㄦ祴璇�', NULL, '{}', '{\"type\":1}', 0, 0, 0, 0, 0, NULL, NULL, 'org.dromara.job.processors.MapReduceProcessorDemo', 1, 2, NULL, 1, '1000', 3);
-
--- ----------------------------
--- Table structure for pj_oms_lock
--- ----------------------------
-DROP TABLE IF EXISTS `pj_oms_lock`;
-CREATE TABLE `pj_oms_lock` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `gmt_create` datetime(6) NULL DEFAULT NULL,
- `gmt_modified` datetime(6) NULL DEFAULT NULL,
- `lock_name` varchar(255) NULL DEFAULT NULL,
- `max_lock_time` bigint(0) NULL DEFAULT NULL,
- `ownerip` varchar(255) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- UNIQUE INDEX `uidx01_oms_lock`(`lock_name`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 6 ROW_FORMAT = Dynamic;
-
--- ----------------------------
--- Table structure for pj_server_info
--- ----------------------------
-DROP TABLE IF EXISTS `pj_server_info`;
-CREATE TABLE `pj_server_info` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `gmt_create` datetime(6) NULL DEFAULT NULL,
- `gmt_modified` datetime(6) NULL DEFAULT NULL,
- `ip` varchar(255) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- UNIQUE INDEX `uidx01_server_info`(`ip`) USING BTREE,
- INDEX `idx01_server_info`(`gmt_modified`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 2 ROW_FORMAT = Dynamic;
-
--- ----------------------------
--- Table structure for pj_user_info
--- ----------------------------
-DROP TABLE IF EXISTS `pj_user_info`;
-CREATE TABLE `pj_user_info` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `email` varchar(255) NULL DEFAULT NULL,
- `extra` varchar(255) NULL DEFAULT NULL,
- `gmt_create` datetime(6) NULL DEFAULT NULL,
- `gmt_modified` datetime(6) NULL DEFAULT NULL,
- `password` varchar(255) NULL DEFAULT NULL,
- `phone` varchar(255) NULL DEFAULT NULL,
- `username` varchar(255) NULL DEFAULT NULL,
- `web_hook` varchar(255) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- INDEX `uidx01_user_info`(`username`) USING BTREE,
- INDEX `uidx02_user_info`(`email`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 1 ROW_FORMAT = Dynamic;
-
--- ----------------------------
--- Table structure for pj_workflow_info
--- ----------------------------
-DROP TABLE IF EXISTS `pj_workflow_info`;
-CREATE TABLE `pj_workflow_info` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `app_id` bigint(0) NULL DEFAULT NULL,
- `extra` varchar(255) NULL DEFAULT NULL,
- `gmt_create` datetime(6) NULL DEFAULT NULL,
- `gmt_modified` datetime(6) NULL DEFAULT NULL,
- `lifecycle` varchar(255) NULL DEFAULT NULL,
- `max_wf_instance_num` int(0) NULL DEFAULT NULL,
- `next_trigger_time` bigint(0) NULL DEFAULT NULL,
- `notify_user_ids` varchar(255) NULL DEFAULT NULL,
- `pedag` longtext NULL,
- `status` int(0) NULL DEFAULT NULL,
- `time_expression` varchar(255) NULL DEFAULT NULL,
- `time_expression_type` int(0) NULL DEFAULT NULL,
- `wf_description` varchar(255) NULL DEFAULT NULL,
- `wf_name` varchar(255) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- INDEX `idx01_workflow_info`(`app_id`, `status`, `time_expression_type`, `next_trigger_time`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 1 ROW_FORMAT = Dynamic;
-
--- ----------------------------
--- Table structure for pj_workflow_instance_info
--- ----------------------------
-DROP TABLE IF EXISTS `pj_workflow_instance_info`;
-CREATE TABLE `pj_workflow_instance_info` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `actual_trigger_time` bigint(0) NULL DEFAULT NULL,
- `app_id` bigint(0) NULL DEFAULT NULL,
- `dag` longtext NULL,
- `expected_trigger_time` bigint(0) NULL DEFAULT NULL,
- `finished_time` bigint(0) NULL DEFAULT NULL,
- `gmt_create` datetime(6) NULL DEFAULT NULL,
- `gmt_modified` datetime(6) NULL DEFAULT NULL,
- `parent_wf_instance_id` bigint(0) NULL DEFAULT NULL,
- `result` longtext NULL,
- `status` int(0) NULL DEFAULT NULL,
- `wf_context` longtext NULL,
- `wf_init_params` longtext NULL,
- `wf_instance_id` bigint(0) NULL DEFAULT NULL,
- `workflow_id` bigint(0) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- UNIQUE INDEX `uidx01_wf_instance`(`wf_instance_id`) USING BTREE,
- INDEX `idx01_wf_instance`(`workflow_id`, `status`, `app_id`, `expected_trigger_time`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 1 ROW_FORMAT = Dynamic;
-
--- ----------------------------
--- Table structure for pj_workflow_node_info
--- ----------------------------
-DROP TABLE IF EXISTS `pj_workflow_node_info`;
-CREATE TABLE `pj_workflow_node_info` (
- `id` bigint(0) NOT NULL AUTO_INCREMENT,
- `app_id` bigint(0) NOT NULL,
- `enable` bit(1) NOT NULL,
- `extra` longtext NULL,
- `gmt_create` datetime(6) NULL,
- `gmt_modified` datetime(6) NULL,
- `job_id` bigint(0) NULL DEFAULT NULL,
- `node_name` varchar(255) NULL DEFAULT NULL,
- `node_params` longtext NULL,
- `skip_when_failed` bit(1) NOT NULL,
- `type` int(0) NULL DEFAULT NULL,
- `workflow_id` bigint(0) NULL DEFAULT NULL,
- PRIMARY KEY (`id`) USING BTREE,
- INDEX `idx01_workflow_node_info`(`workflow_id`, `gmt_create`) USING BTREE
-) ENGINE = InnoDB AUTO_INCREMENT = 1 ROW_FORMAT = Dynamic;
diff --git a/script/sql/ry_vue_5.X.sql b/script/sql/ry_vue_5.X.sql
index ea365bd..396178f 100644
--- a/script/sql/ry_vue_5.X.sql
+++ b/script/sql/ry_vue_5.X.sql
@@ -1,7 +1,6 @@
-- ----------------------------
-- 绗笁鏂瑰钩鍙版巿鏉冭〃
-- ----------------------------
-drop table if exists sys_social;
create table sys_social
(
id bigint not null comment '涓婚敭',
@@ -21,7 +20,7 @@
union_id varchar(255) default null comment '鐢ㄦ埛鐨� unionid',
scope varchar(255) default null comment '鎺堜簣鐨勬潈闄愶紝閮ㄥ垎骞冲彴鍙兘娌℃湁',
token_type varchar(255) default null comment '涓埆骞冲彴鐨勬巿鏉冧俊鎭紝閮ㄥ垎骞冲彴鍙兘娌℃湁',
- id_token varchar(255) default null comment 'id token锛岄儴鍒嗗钩鍙板彲鑳芥病鏈�',
+ id_token varchar(2000) default null comment 'id token锛岄儴鍒嗗钩鍙板彲鑳芥病鏈�',
mac_algorithm varchar(255) default null comment '灏忕背骞冲彴鐢ㄦ埛鐨勯檮甯﹀睘鎬э紝閮ㄥ垎骞冲彴鍙兘娌℃湁',
mac_key varchar(255) default null comment '灏忕背骞冲彴鐢ㄦ埛鐨勯檮甯﹀睘鎬э紝閮ㄥ垎骞冲彴鍙兘娌℃湁',
code varchar(255) default null comment '鐢ㄦ埛鐨勬巿鏉僣ode锛岄儴鍒嗗钩鍙板彲鑳芥病鏈�',
@@ -40,7 +39,6 @@
-- ----------------------------
-- 绉熸埛琛�
-- ----------------------------
-drop table if exists sys_tenant;
create table sys_tenant
(
id bigint(20) not null comment 'id',
@@ -77,7 +75,6 @@
-- ----------------------------
-- 绉熸埛濂楅琛�
-- ----------------------------
-drop table if exists sys_tenant_package;
create table sys_tenant_package (
package_id bigint(20) not null comment '绉熸埛濂楅id',
package_name varchar(20) comment '濂楅鍚嶇О',
@@ -98,13 +95,13 @@
-- ----------------------------
-- 1銆侀儴闂ㄨ〃
-- ----------------------------
-drop table if exists sys_dept;
create table sys_dept (
dept_id bigint(20) not null comment '閮ㄩ棬id',
tenant_id varchar(20) default '000000' comment '绉熸埛缂栧彿',
parent_id bigint(20) default 0 comment '鐖堕儴闂╥d',
ancestors varchar(500) default '' comment '绁栫骇鍒楄〃',
dept_name varchar(30) default '' comment '閮ㄩ棬鍚嶇О',
+ dept_category varchar(100) default null comment '閮ㄩ棬绫诲埆缂栫爜',
order_num int(4) default 0 comment '鏄剧ず椤哄簭',
leader bigint(20) default null comment '璐熻矗浜�',
phone varchar(11) default null comment '鑱旂郴鐢佃瘽',
@@ -124,22 +121,21 @@
-- ----------------------------
-insert into sys_dept values(100, '000000', 0, '0', 'XXX绉戞妧', 0, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-insert into sys_dept values(101, '000000', 100, '0,100', '娣卞湷鎬诲叕鍙�', 1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-insert into sys_dept values(102, '000000', 100, '0,100', '闀挎矙鍒嗗叕鍙�', 2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-insert into sys_dept values(103, '000000', 101, '0,100,101', '鐮斿彂閮ㄩ棬', 1, 1, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-insert into sys_dept values(104, '000000', 101, '0,100,101', '甯傚満閮ㄩ棬', 2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-insert into sys_dept values(105, '000000', 101, '0,100,101', '娴嬭瘯閮ㄩ棬', 3, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-insert into sys_dept values(106, '000000', 101, '0,100,101', '璐㈠姟閮ㄩ棬', 4, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-insert into sys_dept values(107, '000000', 101, '0,100,101', '杩愮淮閮ㄩ棬', 5, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-insert into sys_dept values(108, '000000', 102, '0,100,102', '甯傚満閮ㄩ棬', 1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-insert into sys_dept values(109, '000000', 102, '0,100,102', '璐㈠姟閮ㄩ棬', 2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(100, '000000', 0, '0', 'XXX绉戞妧', null,0, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(101, '000000', 100, '0,100', '娣卞湷鎬诲叕鍙�', null,1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(102, '000000', 100, '0,100', '闀挎矙鍒嗗叕鍙�', null,2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(103, '000000', 101, '0,100,101', '鐮斿彂閮ㄩ棬', null,1, 1, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(104, '000000', 101, '0,100,101', '甯傚満閮ㄩ棬', null,2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(105, '000000', 101, '0,100,101', '娴嬭瘯閮ㄩ棬', null,3, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(106, '000000', 101, '0,100,101', '璐㈠姟閮ㄩ棬', null,4, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(107, '000000', 101, '0,100,101', '杩愮淮閮ㄩ棬', null,5, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(108, '000000', 102, '0,100,102', '甯傚満閮ㄩ棬', null,1, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
+insert into sys_dept values(109, '000000', 102, '0,100,102', '璐㈠姟閮ㄩ棬', null,2, null, '15888888888', 'xxx@qq.com', '0', '0', 103, 1, sysdate(), null, null);
-- ----------------------------
-- 2銆佺敤鎴蜂俊鎭〃
-- ----------------------------
-drop table if exists sys_user;
create table sys_user (
user_id bigint(20) not null comment '鐢ㄦ埛ID',
tenant_id varchar(20) default '000000' comment '绉熸埛缂栧彿',
@@ -169,18 +165,19 @@
-- 鍒濆鍖�-鐢ㄦ埛淇℃伅琛ㄦ暟鎹�
-- ----------------------------
insert into sys_user values(1, '000000', 103, 'admin', '鐤媯鐨勭嫯瀛怢i', 'sys_user', 'crazyLionLi@163.com', '15888888888', '1', null, '$2a$10$7JB720yubVSZvUI0rEqK/.VqGOZTH.ulu33dHOiBE8ByOhJIrdAu2', '0', '0', '127.0.0.1', sysdate(), 103, 1, sysdate(), null, null, '绠$悊鍛�');
-insert into sys_user values(2, '000000', 105, 'lionli', '鐤媯鐨勭嫯瀛怢i', 'sys_user', 'crazyLionLi@qq.com', '15666666666', '1', null, '$2a$10$7JB720yubVSZvUI0rEqK/.VqGOZTH.ulu33dHOiBE8ByOhJIrdAu2', '0', '0', '127.0.0.1', sysdate(), 103, 1, sysdate(), null, null, '娴嬭瘯鍛�');
-
+insert into sys_user values(3, '000000', 108, 'test', '鏈儴闂ㄥ強浠ヤ笅 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', sysdate(), 103, 1, sysdate(), 3, sysdate(), null);
+insert into sys_user values(4, '000000', 102, 'test1', '浠呮湰浜� 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', sysdate(), 103, 1, sysdate(), 4, sysdate(), null);
-- ----------------------------
-- 3銆佸矖浣嶄俊鎭〃
-- ----------------------------
-drop table if exists sys_post;
create table sys_post
(
post_id bigint(20) not null comment '宀椾綅ID',
tenant_id varchar(20) default '000000' comment '绉熸埛缂栧彿',
+ dept_id bigint(20) not null comment '閮ㄩ棬id',
post_code varchar(64) not null comment '宀椾綅缂栫爜',
+ post_category varchar(100) default null comment '宀椾綅绫诲埆缂栫爜',
post_name varchar(50) not null comment '宀椾綅鍚嶇О',
post_sort int(4) not null comment '鏄剧ず椤哄簭',
status char(1) not null comment '鐘舵�侊紙0姝e父 1鍋滅敤锛�',
@@ -196,16 +193,15 @@
-- ----------------------------
-- 鍒濆鍖�-宀椾綅淇℃伅琛ㄦ暟鎹�
-- ----------------------------
-insert into sys_post values(1, '000000', 'ceo', '钁d簨闀�', 1, '0', 103, 1, sysdate(), null, null, '');
-insert into sys_post values(2, '000000', 'se', '椤圭洰缁忕悊', 2, '0', 103, 1, sysdate(), null, null, '');
-insert into sys_post values(3, '000000', 'hr', '浜哄姏璧勬簮', 3, '0', 103, 1, sysdate(), null, null, '');
-insert into sys_post values(4, '000000', 'user', '鏅�氬憳宸�', 4, '0', 103, 1, sysdate(), null, null, '');
+insert into sys_post values(1, '000000', 103, 'ceo', null, '钁d簨闀�', 1, '0', 103, 1, sysdate(), null, null, '');
+insert into sys_post values(2, '000000', 100, 'se', null, '椤圭洰缁忕悊', 2, '0', 103, 1, sysdate(), null, null, '');
+insert into sys_post values(3, '000000', 100, 'hr', null, '浜哄姏璧勬簮', 3, '0', 103, 1, sysdate(), null, null, '');
+insert into sys_post values(4, '000000', 100, 'user', null, '鏅�氬憳宸�', 4, '0', 103, 1, sysdate(), null, null, '');
-- ----------------------------
-- 4銆佽鑹蹭俊鎭〃
-- ----------------------------
-drop table if exists sys_role;
create table sys_role (
role_id bigint(20) not null comment '瑙掕壊ID',
tenant_id varchar(20) default '000000' comment '绉熸埛缂栧彿',
@@ -230,13 +226,12 @@
-- 鍒濆鍖�-瑙掕壊淇℃伅琛ㄦ暟鎹�
-- ----------------------------
insert into sys_role values(1, '000000', '瓒呯骇绠$悊鍛�', 'superadmin', 1, 1, 1, 1, '0', '0', 103, 1, sysdate(), null, null, '瓒呯骇绠$悊鍛�');
-insert into sys_role values(2, '000000', '鏅�氳鑹�', 'common', 2, 2, 1, 1, '0', '0', 103, 1, sysdate(), null, null, '鏅�氳鑹�');
-
+insert into sys_role values(3, '000000', '鏈儴闂ㄥ強浠ヤ笅', 'test1', 3, 4, 1, 1, '0', '0', 103, 1, sysdate(), null, null, '');
+insert into sys_role values(4, '000000', '浠呮湰浜�', 'test2', 4, 5, 1, 1, '0', '0', 103, 1, sysdate(), null, null, '');
-- ----------------------------
-- 5銆佽彍鍗曟潈闄愯〃
-- ----------------------------
-drop table if exists sys_menu;
create table sys_menu (
menu_id bigint(20) not null comment '鑿滃崟ID',
menu_name varchar(50) not null comment '鑿滃崟鍚嶇О',
@@ -270,6 +265,7 @@
insert into sys_menu values('2', '绯荤粺鐩戞帶', '0', '3', 'monitor', null, '', 1, 0, 'M', '0', '0', '', 'monitor', 103, 1, sysdate(), null, null, '绯荤粺鐩戞帶鐩綍');
insert into sys_menu values('3', '绯荤粺宸ュ叿', '0', '4', 'tool', null, '', 1, 0, 'M', '0', '0', '', 'tool', 103, 1, sysdate(), null, null, '绯荤粺宸ュ叿鐩綍');
insert into sys_menu values('4', 'PLUS瀹樼綉', '0', '5', 'https://gitee.com/dromara/RuoYi-Vue-Plus', null, '', 0, 0, 'M', '0', '0', '', 'guide', 103, 1, sysdate(), null, null, 'RuoYi-Vue-Plus瀹樼綉鍦板潃');
+insert into sys_menu values('5', '娴嬭瘯鑿滃崟', '0', '5', 'demo', null, '', 1, 0, 'M', '0', '0', '', 'star', 103, 1, sysdate(), null, null, '娴嬭瘯鑿滃崟');
-- 浜岀骇鑿滃崟
insert into sys_menu values('100', '鐢ㄦ埛绠$悊', '1', '1', 'user', 'system/user/index', '', 1, 0, 'C', '0', '0', 'system:user:list', 'user', 103, 1, sysdate(), null, null, '鐢ㄦ埛绠$悊鑿滃崟');
insert into sys_menu values('101', '瑙掕壊绠$悊', '1', '2', 'role', 'system/role/index', '', 1, 0, 'C', '0', '0', 'system:role:list', 'peoples', 103, 1, sysdate(), null, null, '瑙掕壊绠$悊鑿滃崟');
@@ -292,8 +288,8 @@
insert into sys_menu values('117', 'Admin鐩戞帶', '2', '5', 'Admin', 'monitor/admin/index', '', 1, 0, 'C', '0', '0', 'monitor:admin:list', 'dashboard', 103, 1, sysdate(), null, null, 'Admin鐩戞帶鑿滃崟');
-- oss鑿滃崟
insert into sys_menu values('118', '鏂囦欢绠$悊', '1', '10', 'oss', 'system/oss/index', '', 1, 0, 'C', '0', '0', 'system:oss:list', 'upload', 103, 1, sysdate(), null, null, '鏂囦欢绠$悊鑿滃崟');
--- powerjob server鎺у埗鍙�
-insert into sys_menu values('120', '浠诲姟璋冨害涓績', '2', '5', 'powerjob', 'monitor/powerjob/index', '', 1, 0, 'C', '0', '0', 'monitor:powerjob:list', 'job', 103, 1, sysdate(), null, null, 'PowerJob鎺у埗鍙拌彍鍗�');
+-- snail-job server鎺у埗鍙�
+insert into sys_menu values('120', '浠诲姟璋冨害涓績', '2', '6', 'snailjob', 'monitor/snailjob/index', '', 1, 0, 'C', '0', '0', 'monitor:snailjob:list', 'job', 103, 1, sysdate(), null, null, 'SnailJob鎺у埗鍙拌彍鍗�');
-- 涓夌骇鑿滃崟
insert into sys_menu values('500', '鎿嶄綔鏃ュ織', '108', '1', 'operlog', 'monitor/operlog/index', '', 1, 0, 'C', '0', '0', 'monitor:operlog:list', 'form', 103, 1, sysdate(), null, null, '鎿嶄綔鏃ュ織鑿滃崟');
@@ -393,11 +389,23 @@
insert into sys_menu values('1063', '瀹㈡埛绔鐞嗕慨鏀�', '123', '3', '#', '', '', 1, 0, 'F', '0', '0', 'system:client:edit', '#', 103, 1, sysdate(), null, null, '');
insert into sys_menu values('1064', '瀹㈡埛绔鐞嗗垹闄�', '123', '4', '#', '', '', 1, 0, 'F', '0', '0', 'system:client:remove', '#', 103, 1, sysdate(), null, null, '');
insert into sys_menu values('1065', '瀹㈡埛绔鐞嗗鍑�', '123', '5', '#', '', '', 1, 0, 'F', '0', '0', 'system:client:export', '#', 103, 1, sysdate(), null, null, '');
+-- 娴嬭瘯鑿滃崟
+insert into sys_menu values('1500', '娴嬭瘯鍗曡〃', '5', '1', 'demo', 'demo/demo/index', '', 1, 0, 'C', '0', '0', 'demo:demo:list', '#', 103, 1, sysdate(), null, null, '娴嬭瘯鍗曡〃鑿滃崟');
+insert into sys_menu values('1501', '娴嬭瘯鍗曡〃鏌ヨ', '1500', '1', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:query', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values('1502', '娴嬭瘯鍗曡〃鏂板', '1500', '2', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:add', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values('1503', '娴嬭瘯鍗曡〃淇敼', '1500', '3', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:edit', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values('1504', '娴嬭瘯鍗曡〃鍒犻櫎', '1500', '4', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:remove', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values('1505', '娴嬭瘯鍗曡〃瀵煎嚭', '1500', '5', '#', '', '', 1, 0, 'F', '0', '0', 'demo:demo:export', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values('1506', '娴嬭瘯鏍戣〃', '5', '1', 'tree', 'demo/tree/index', '', 1, 0, 'C', '0', '0', 'demo:tree:list', '#', 103, 1, sysdate(), null, null, '娴嬭瘯鏍戣〃鑿滃崟');
+insert into sys_menu values('1507', '娴嬭瘯鏍戣〃鏌ヨ', '1506', '1', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:query', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values('1508', '娴嬭瘯鏍戣〃鏂板', '1506', '2', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:add', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values('1509', '娴嬭瘯鏍戣〃淇敼', '1506', '3', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:edit', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values('1510', '娴嬭瘯鏍戣〃鍒犻櫎', '1506', '4', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:remove', '#', 103, 1, sysdate(), null, null, '');
+insert into sys_menu values('1511', '娴嬭瘯鏍戣〃瀵煎嚭', '1506', '5', '#', '', '', 1, 0, 'F', '0', '0', 'demo:tree:export', '#', 103, 1, sysdate(), null, null, '');
-- ----------------------------
-- 6銆佺敤鎴峰拰瑙掕壊鍏宠仈琛� 鐢ㄦ埛N-1瑙掕壊
-- ----------------------------
-drop table if exists sys_user_role;
create table sys_user_role (
user_id bigint(20) not null comment '鐢ㄦ埛ID',
role_id bigint(20) not null comment '瑙掕壊ID',
@@ -408,13 +416,12 @@
-- 鍒濆鍖�-鐢ㄦ埛鍜岃鑹插叧鑱旇〃鏁版嵁
-- ----------------------------
insert into sys_user_role values ('1', '1');
-insert into sys_user_role values ('2', '2');
-
+insert into sys_user_role values ('3', '3');
+insert into sys_user_role values ('4', '4');
-- ----------------------------
-- 7銆佽鑹插拰鑿滃崟鍏宠仈琛� 瑙掕壊1-N鑿滃崟
-- ----------------------------
-drop table if exists sys_role_menu;
create table sys_role_menu (
role_id bigint(20) not null comment '瑙掕壊ID',
menu_id bigint(20) not null comment '鑿滃崟ID',
@@ -424,95 +431,93 @@
-- ----------------------------
-- 鍒濆鍖�-瑙掕壊鍜岃彍鍗曞叧鑱旇〃鏁版嵁
-- ----------------------------
-insert into sys_role_menu values ('2', '1');
-insert into sys_role_menu values ('2', '2');
-insert into sys_role_menu values ('2', '3');
-insert into sys_role_menu values ('2', '4');
-insert into sys_role_menu values ('2', '100');
-insert into sys_role_menu values ('2', '101');
-insert into sys_role_menu values ('2', '102');
-insert into sys_role_menu values ('2', '103');
-insert into sys_role_menu values ('2', '104');
-insert into sys_role_menu values ('2', '105');
-insert into sys_role_menu values ('2', '106');
-insert into sys_role_menu values ('2', '107');
-insert into sys_role_menu values ('2', '108');
-insert into sys_role_menu values ('2', '109');
-insert into sys_role_menu values ('2', '110');
-insert into sys_role_menu values ('2', '111');
-insert into sys_role_menu values ('2', '112');
-insert into sys_role_menu values ('2', '113');
-insert into sys_role_menu values ('2', '114');
-insert into sys_role_menu values ('2', '115');
-insert into sys_role_menu values ('2', '116');
-insert into sys_role_menu values ('2', '500');
-insert into sys_role_menu values ('2', '501');
-insert into sys_role_menu values ('2', '1000');
-insert into sys_role_menu values ('2', '1001');
-insert into sys_role_menu values ('2', '1002');
-insert into sys_role_menu values ('2', '1003');
-insert into sys_role_menu values ('2', '1004');
-insert into sys_role_menu values ('2', '1005');
-insert into sys_role_menu values ('2', '1006');
-insert into sys_role_menu values ('2', '1007');
-insert into sys_role_menu values ('2', '1008');
-insert into sys_role_menu values ('2', '1009');
-insert into sys_role_menu values ('2', '1010');
-insert into sys_role_menu values ('2', '1011');
-insert into sys_role_menu values ('2', '1012');
-insert into sys_role_menu values ('2', '1013');
-insert into sys_role_menu values ('2', '1014');
-insert into sys_role_menu values ('2', '1015');
-insert into sys_role_menu values ('2', '1016');
-insert into sys_role_menu values ('2', '1017');
-insert into sys_role_menu values ('2', '1018');
-insert into sys_role_menu values ('2', '1019');
-insert into sys_role_menu values ('2', '1020');
-insert into sys_role_menu values ('2', '1021');
-insert into sys_role_menu values ('2', '1022');
-insert into sys_role_menu values ('2', '1023');
-insert into sys_role_menu values ('2', '1024');
-insert into sys_role_menu values ('2', '1025');
-insert into sys_role_menu values ('2', '1026');
-insert into sys_role_menu values ('2', '1027');
-insert into sys_role_menu values ('2', '1028');
-insert into sys_role_menu values ('2', '1029');
-insert into sys_role_menu values ('2', '1030');
-insert into sys_role_menu values ('2', '1031');
-insert into sys_role_menu values ('2', '1032');
-insert into sys_role_menu values ('2', '1033');
-insert into sys_role_menu values ('2', '1034');
-insert into sys_role_menu values ('2', '1035');
-insert into sys_role_menu values ('2', '1036');
-insert into sys_role_menu values ('2', '1037');
-insert into sys_role_menu values ('2', '1038');
-insert into sys_role_menu values ('2', '1039');
-insert into sys_role_menu values ('2', '1040');
-insert into sys_role_menu values ('2', '1041');
-insert into sys_role_menu values ('2', '1042');
-insert into sys_role_menu values ('2', '1043');
-insert into sys_role_menu values ('2', '1044');
-insert into sys_role_menu values ('2', '1045');
-insert into sys_role_menu values ('2', '1050');
-insert into sys_role_menu values ('2', '1046');
-insert into sys_role_menu values ('2', '1047');
-insert into sys_role_menu values ('2', '1048');
-insert into sys_role_menu values ('2', '1055');
-insert into sys_role_menu values ('2', '1056');
-insert into sys_role_menu values ('2', '1057');
-insert into sys_role_menu values ('2', '1058');
-insert into sys_role_menu values ('2', '1059');
-insert into sys_role_menu values ('2', '1060');
-insert into sys_role_menu values ('2', '1061');
-insert into sys_role_menu values ('2', '1062');
-insert into sys_role_menu values ('2', '1063');
-insert into sys_role_menu values ('2', '1064');
-insert into sys_role_menu values ('2', '1065');
+insert into sys_role_menu values ('3', '1');
+insert into sys_role_menu values ('3', '5');
+insert into sys_role_menu values ('3', '100');
+insert into sys_role_menu values ('3', '101');
+insert into sys_role_menu values ('3', '102');
+insert into sys_role_menu values ('3', '103');
+insert into sys_role_menu values ('3', '104');
+insert into sys_role_menu values ('3', '105');
+insert into sys_role_menu values ('3', '106');
+insert into sys_role_menu values ('3', '107');
+insert into sys_role_menu values ('3', '108');
+insert into sys_role_menu values ('3', '500');
+insert into sys_role_menu values ('3', '501');
+insert into sys_role_menu values ('3', '1001');
+insert into sys_role_menu values ('3', '1002');
+insert into sys_role_menu values ('3', '1003');
+insert into sys_role_menu values ('3', '1004');
+insert into sys_role_menu values ('3', '1005');
+insert into sys_role_menu values ('3', '1006');
+insert into sys_role_menu values ('3', '1007');
+insert into sys_role_menu values ('3', '1008');
+insert into sys_role_menu values ('3', '1009');
+insert into sys_role_menu values ('3', '1010');
+insert into sys_role_menu values ('3', '1011');
+insert into sys_role_menu values ('3', '1012');
+insert into sys_role_menu values ('3', '1013');
+insert into sys_role_menu values ('3', '1014');
+insert into sys_role_menu values ('3', '1015');
+insert into sys_role_menu values ('3', '1016');
+insert into sys_role_menu values ('3', '1017');
+insert into sys_role_menu values ('3', '1018');
+insert into sys_role_menu values ('3', '1019');
+insert into sys_role_menu values ('3', '1020');
+insert into sys_role_menu values ('3', '1021');
+insert into sys_role_menu values ('3', '1022');
+insert into sys_role_menu values ('3', '1023');
+insert into sys_role_menu values ('3', '1024');
+insert into sys_role_menu values ('3', '1025');
+insert into sys_role_menu values ('3', '1026');
+insert into sys_role_menu values ('3', '1027');
+insert into sys_role_menu values ('3', '1028');
+insert into sys_role_menu values ('3', '1029');
+insert into sys_role_menu values ('3', '1030');
+insert into sys_role_menu values ('3', '1031');
+insert into sys_role_menu values ('3', '1032');
+insert into sys_role_menu values ('3', '1033');
+insert into sys_role_menu values ('3', '1034');
+insert into sys_role_menu values ('3', '1035');
+insert into sys_role_menu values ('3', '1036');
+insert into sys_role_menu values ('3', '1037');
+insert into sys_role_menu values ('3', '1038');
+insert into sys_role_menu values ('3', '1039');
+insert into sys_role_menu values ('3', '1040');
+insert into sys_role_menu values ('3', '1041');
+insert into sys_role_menu values ('3', '1042');
+insert into sys_role_menu values ('3', '1043');
+insert into sys_role_menu values ('3', '1044');
+insert into sys_role_menu values ('3', '1045');
+insert into sys_role_menu values ('3', '1500');
+insert into sys_role_menu values ('3', '1501');
+insert into sys_role_menu values ('3', '1502');
+insert into sys_role_menu values ('3', '1503');
+insert into sys_role_menu values ('3', '1504');
+insert into sys_role_menu values ('3', '1505');
+insert into sys_role_menu values ('3', '1506');
+insert into sys_role_menu values ('3', '1507');
+insert into sys_role_menu values ('3', '1508');
+insert into sys_role_menu values ('3', '1509');
+insert into sys_role_menu values ('3', '1510');
+insert into sys_role_menu values ('3', '1511');
+insert into sys_role_menu values ('4', '5');
+insert into sys_role_menu values ('4', '1500');
+insert into sys_role_menu values ('4', '1501');
+insert into sys_role_menu values ('4', '1502');
+insert into sys_role_menu values ('4', '1503');
+insert into sys_role_menu values ('4', '1504');
+insert into sys_role_menu values ('4', '1505');
+insert into sys_role_menu values ('4', '1506');
+insert into sys_role_menu values ('4', '1507');
+insert into sys_role_menu values ('4', '1508');
+insert into sys_role_menu values ('4', '1509');
+insert into sys_role_menu values ('4', '1510');
+insert into sys_role_menu values ('4', '1511');
-- ----------------------------
-- 8銆佽鑹插拰閮ㄩ棬鍏宠仈琛� 瑙掕壊1-N閮ㄩ棬
-- ----------------------------
-drop table if exists sys_role_dept;
create table sys_role_dept (
role_id bigint(20) not null comment '瑙掕壊ID',
dept_id bigint(20) not null comment '閮ㄩ棬ID',
@@ -520,17 +525,8 @@
) engine=innodb comment = '瑙掕壊鍜岄儴闂ㄥ叧鑱旇〃';
-- ----------------------------
--- 鍒濆鍖�-瑙掕壊鍜岄儴闂ㄥ叧鑱旇〃鏁版嵁
--- ----------------------------
-insert into sys_role_dept values ('2', '100');
-insert into sys_role_dept values ('2', '101');
-insert into sys_role_dept values ('2', '105');
-
-
--- ----------------------------
-- 9銆佺敤鎴蜂笌宀椾綅鍏宠仈琛� 鐢ㄦ埛1-N宀椾綅
-- ----------------------------
-drop table if exists sys_user_post;
create table sys_user_post
(
user_id bigint(20) not null comment '鐢ㄦ埛ID',
@@ -542,13 +538,10 @@
-- 鍒濆鍖�-鐢ㄦ埛涓庡矖浣嶅叧鑱旇〃鏁版嵁
-- ----------------------------
insert into sys_user_post values ('1', '1');
-insert into sys_user_post values ('2', '2');
-
-- ----------------------------
-- 10銆佹搷浣滄棩蹇楄褰�
-- ----------------------------
-drop table if exists sys_oper_log;
create table sys_oper_log (
oper_id bigint(20) not null comment '鏃ュ織涓婚敭',
tenant_id varchar(20) default '000000' comment '绉熸埛缂栧彿',
@@ -578,7 +571,6 @@
-- ----------------------------
-- 11銆佸瓧鍏哥被鍨嬭〃
-- ----------------------------
-drop table if exists sys_dict_type;
create table sys_dict_type
(
dict_id bigint(20) not null comment '瀛楀吀涓婚敭',
@@ -610,7 +602,6 @@
-- ----------------------------
-- 12銆佸瓧鍏告暟鎹〃
-- ----------------------------
-drop table if exists sys_dict_data;
create table sys_dict_data
(
dict_code bigint(20) not null comment '瀛楀吀缂栫爜',
@@ -670,7 +661,6 @@
-- ----------------------------
-- 13銆佸弬鏁伴厤缃〃
-- ----------------------------
-drop table if exists sys_config;
create table sys_config (
config_id bigint(20) not null comment '鍙傛暟涓婚敭',
tenant_id varchar(20) default '000000' comment '绉熸埛缂栧彿',
@@ -697,7 +687,6 @@
-- ----------------------------
-- 14銆佺郴缁熻闂褰�
-- ----------------------------
-drop table if exists sys_logininfor;
create table sys_logininfor (
info_id bigint(20) not null comment '璁块棶ID',
tenant_id varchar(20) default '000000' comment '绉熸埛缂栧彿',
@@ -720,7 +709,6 @@
-- ----------------------------
-- 17銆侀�氱煡鍏憡琛�
-- ----------------------------
-drop table if exists sys_notice;
create table sys_notice (
notice_id bigint(20) not null comment '鍏憡ID',
tenant_id varchar(20) default '000000' comment '绉熸埛缂栧彿',
@@ -747,7 +735,6 @@
-- ----------------------------
-- 18銆佷唬鐮佺敓鎴愪笟鍔¤〃
-- ----------------------------
-drop table if exists gen_table;
create table gen_table (
table_id bigint(20) not null comment '缂栧彿',
data_name varchar(200) default '' comment '鏁版嵁婧愬悕绉�',
@@ -778,7 +765,6 @@
-- ----------------------------
-- 19銆佷唬鐮佺敓鎴愪笟鍔¤〃瀛楁
-- ----------------------------
-drop table if exists gen_table_column;
create table gen_table_column (
column_id bigint(20) not null comment '缂栧彿',
table_id bigint(20) comment '褰掑睘琛ㄧ紪鍙�',
@@ -809,7 +795,6 @@
-- ----------------------------
-- OSS瀵硅薄瀛樺偍琛�
-- ----------------------------
-drop table if exists sys_oss;
create table sys_oss (
oss_id bigint(20) not null comment '瀵硅薄瀛樺偍涓婚敭',
tenant_id varchar(20) default '000000' comment '绉熸埛缂栧彿',
@@ -829,9 +814,8 @@
-- ----------------------------
-- OSS瀵硅薄瀛樺偍鍔ㄦ�侀厤缃〃
-- ----------------------------
-drop table if exists sys_oss_config;
create table sys_oss_config (
- oss_config_id bigint(20) not null comment '涓诲缓',
+ oss_config_id bigint(20) not null comment '涓婚敭',
tenant_id varchar(20) default '000000'comment '绉熸埛缂栧彿',
config_key varchar(20) not null default '' comment '閰嶇疆key',
access_key varchar(255) default '' comment 'accessKey',
@@ -863,7 +847,6 @@
-- ----------------------------
-- 绯荤粺鎺堟潈琛�
-- ----------------------------
-drop table if exists sys_client;
create table sys_client (
id bigint(20) not null comment 'id',
client_id varchar(64) default null comment '瀹㈡埛绔痠d',
@@ -885,3 +868,69 @@
insert into sys_client values (1, 'e5cd7e4891bf95d1d19206ce24a7b32e', 'pc', 'pc123', 'password,social', 'pc', 1800, 604800, 0, 0, 103, 1, sysdate(), 1, sysdate());
insert into sys_client values (2, '428a8310cd442757ae699df5d894f051', 'app', 'app123', 'password,sms,social', 'android', 1800, 604800, 0, 0, 103, 1, sysdate(), 1, sysdate());
+
+
+CREATE TABLE test_demo
+(
+ id bigint(0) NOT NULL COMMENT '涓婚敭',
+ tenant_id varchar(20) NULL DEFAULT '000000' COMMENT '绉熸埛缂栧彿',
+ dept_id bigint(0) NULL DEFAULT NULL COMMENT '閮ㄩ棬id',
+ user_id bigint(0) NULL DEFAULT NULL COMMENT '鐢ㄦ埛id',
+ order_num int(0) NULL DEFAULT 0 COMMENT '鎺掑簭鍙�',
+ test_key varchar(255) NULL DEFAULT NULL COMMENT 'key閿�',
+ value varchar(255) NULL DEFAULT NULL COMMENT '鍊�',
+ version int(0) NULL DEFAULT 0 COMMENT '鐗堟湰',
+ create_dept bigint(0) NULL DEFAULT NULL COMMENT '鍒涘缓閮ㄩ棬',
+ create_time datetime(0) NULL DEFAULT NULL COMMENT '鍒涘缓鏃堕棿',
+ create_by bigint(0) NULL DEFAULT NULL COMMENT '鍒涘缓浜�',
+ update_time datetime(0) NULL DEFAULT NULL COMMENT '鏇存柊鏃堕棿',
+ update_by bigint(0) NULL DEFAULT NULL COMMENT '鏇存柊浜�',
+ del_flag int(0) NULL DEFAULT 0 COMMENT '鍒犻櫎鏍囧織',
+ PRIMARY KEY (id) USING BTREE
+) ENGINE = InnoDB COMMENT = '娴嬭瘯鍗曡〃';
+
+CREATE TABLE test_tree
+(
+ id bigint(0) NOT NULL COMMENT '涓婚敭',
+ tenant_id varchar(20) NULL DEFAULT '000000' COMMENT '绉熸埛缂栧彿',
+ parent_id bigint(0) NULL DEFAULT 0 COMMENT '鐖秈d',
+ dept_id bigint(0) NULL DEFAULT NULL COMMENT '閮ㄩ棬id',
+ user_id bigint(0) NULL DEFAULT NULL COMMENT '鐢ㄦ埛id',
+ tree_name varchar(255) NULL DEFAULT NULL COMMENT '鍊�',
+ version int(0) NULL DEFAULT 0 COMMENT '鐗堟湰',
+ create_dept bigint(0) NULL DEFAULT NULL COMMENT '鍒涘缓閮ㄩ棬',
+ create_time datetime(0) NULL DEFAULT NULL COMMENT '鍒涘缓鏃堕棿',
+ create_by bigint(0) NULL DEFAULT NULL COMMENT '鍒涘缓浜�',
+ update_time datetime(0) NULL DEFAULT NULL COMMENT '鏇存柊鏃堕棿',
+ update_by bigint(0) NULL DEFAULT NULL COMMENT '鏇存柊浜�',
+ del_flag int(0) NULL DEFAULT 0 COMMENT '鍒犻櫎鏍囧織',
+ PRIMARY KEY (id) USING BTREE
+) ENGINE = InnoDB COMMENT = '娴嬭瘯鏍戣〃';
+
+INSERT INTO test_demo VALUES (1, '000000', 102, 4, 1, '娴嬭瘯鏁版嵁鏉冮檺', '娴嬭瘯', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (2, '000000', 102, 3, 2, '瀛愯妭鐐�1', '111', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (3, '000000', 102, 3, 3, '瀛愯妭鐐�2', '222', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (4, '000000', 108, 4, 4, '娴嬭瘯鏁版嵁', 'demo', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (5, '000000', 108, 3, 13, '瀛愯妭鐐�11', '1111', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (6, '000000', 108, 3, 12, '瀛愯妭鐐�22', '2222', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (7, '000000', 108, 3, 11, '瀛愯妭鐐�33', '3333', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (8, '000000', 108, 3, 10, '瀛愯妭鐐�44', '4444', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (9, '000000', 108, 3, 9, '瀛愯妭鐐�55', '5555', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (10, '000000', 108, 3, 8, '瀛愯妭鐐�66', '6666', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (11, '000000', 108, 3, 7, '瀛愯妭鐐�77', '7777', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (12, '000000', 108, 3, 6, '瀛愯妭鐐�88', '8888', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_demo VALUES (13, '000000', 108, 3, 5, '瀛愯妭鐐�99', '9999', 0, 103, sysdate(), 1, NULL, NULL, 0);
+
+INSERT INTO test_tree VALUES (1, '000000', 0, 102, 4, '娴嬭瘯鏁版嵁鏉冮檺', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (2, '000000', 1, 102, 3, '瀛愯妭鐐�1', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (3, '000000', 2, 102, 3, '瀛愯妭鐐�2', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (4, '000000', 0, 108, 4, '娴嬭瘯鏍�1', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (5, '000000', 4, 108, 3, '瀛愯妭鐐�11', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (6, '000000', 4, 108, 3, '瀛愯妭鐐�22', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (7, '000000', 4, 108, 3, '瀛愯妭鐐�33', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (8, '000000', 5, 108, 3, '瀛愯妭鐐�44', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (9, '000000', 6, 108, 3, '瀛愯妭鐐�55', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (10, '000000', 7, 108, 3, '瀛愯妭鐐�66', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (11, '000000', 7, 108, 3, '瀛愯妭鐐�77', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (12, '000000', 10, 108, 3, '瀛愯妭鐐�88', 0, 103, sysdate(), 1, NULL, NULL, 0);
+INSERT INTO test_tree VALUES (13, '000000', 10, 108, 3, '瀛愯妭鐐�99', 0, 103, sysdate(), 1, NULL, NULL, 0);
diff --git a/script/sql/snail_job.sql b/script/sql/snail_job.sql
new file mode 100644
index 0000000..ce93e11
--- /dev/null
+++ b/script/sql/snail_job.sql
@@ -0,0 +1,509 @@
+SET NAMES utf8mb4;
+
+CREATE TABLE `sj_namespace`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `name` varchar(64) NOT NULL COMMENT '鍚嶇О',
+ `unique_id` varchar(64) NOT NULL COMMENT '鍞竴id',
+ `description` varchar(256) NOT NULL DEFAULT '' COMMENT '鎻忚堪',
+ `deleted` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閫昏緫鍒犻櫎 1銆佸垹闄�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_name` (`name`),
+ UNIQUE KEY `uk_unique_id` (`unique_id`)
+) ENGINE = InnoDB
+ DEFAULT CHARSET = utf8mb4 COMMENT ='鍛藉悕绌洪棿';
+
+INSERT INTO `sj_namespace` VALUES (1, 'Development', 'dev', '', 0, now(), now());
+INSERT INTO `sj_namespace` VALUES (2, 'Production', 'prod', '', 0, now(), now());
+
+CREATE TABLE `sj_group_config`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL DEFAULT '' COMMENT '缁勫悕绉�',
+ `description` varchar(256) NOT NULL DEFAULT '' COMMENT '缁勬弿杩�',
+ `token` varchar(64) NOT NULL DEFAULT 'SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT' COMMENT 'token',
+ `group_status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '缁勭姸鎬� 0銆佹湭鍚敤 1銆佸惎鐢�',
+ `version` int(11) NOT NULL COMMENT '鐗堟湰鍙�',
+ `group_partition` int(11) NOT NULL COMMENT '鍒嗗尯',
+ `id_generator_mode` tinyint(4) NOT NULL DEFAULT 1 COMMENT '鍞竴id鐢熸垚妯″紡 榛樿鍙锋妯″紡',
+ `init_scene` tinyint(4) NOT NULL DEFAULT 0 COMMENT '鏄惁鍒濆鍖栧満鏅� 0:鍚� 1:鏄�',
+ `bucket_index` int(11) NOT NULL DEFAULT 0 COMMENT 'bucket',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `uk_namespace_id_group_name` (`namespace_id`, `group_name`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='缁勯厤缃�';
+
+INSERT INTO `sj_group_config` VALUES (1, 'dev', 'ruoyi_group', '', 'SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT', 1, 1, 0, 1, 1, 4, now(), now());
+
+CREATE TABLE `sj_notify_config`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `business_id` varchar(64) NOT NULL COMMENT '涓氬姟id (job_id鎴杦orkflow_id鎴杝cene_name)',
+ `system_task_type` tinyint(4) NOT NULL DEFAULT 3 COMMENT '浠诲姟绫诲瀷 1. 閲嶈瘯浠诲姟 2. 閲嶈瘯鍥炶皟 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟',
+ `notify_status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閫氱煡鐘舵�� 0銆佹湭鍚敤 1銆佸惎鐢�',
+ `recipient_ids` varchar(128) NOT NULL COMMENT '鎺ユ敹浜篿d鍒楄〃',
+ `notify_threshold` int(11) NOT NULL DEFAULT 0 COMMENT '閫氱煡闃堝��',
+ `notify_scene` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閫氱煡鍦烘櫙',
+ `rate_limiter_status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '闄愭祦鐘舵�� 0銆佹湭鍚敤 1銆佸惎鐢�',
+ `rate_limiter_threshold` int(11) NOT NULL DEFAULT 0 COMMENT '姣忕闄愭祦闃堝��',
+ `description` varchar(256) NOT NULL DEFAULT '' COMMENT '鎻忚堪',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_namespace_id_group_name_scene_name` (`namespace_id`, `group_name`, `business_id`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='閫氱煡閰嶇疆';
+
+CREATE TABLE `sj_notify_recipient`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `recipient_name` varchar(64) NOT NULL COMMENT '鎺ユ敹浜哄悕绉�',
+ `notify_type` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閫氱煡绫诲瀷 1銆侀拤閽� 2銆侀偖浠� 3銆佷紒涓氬井淇� 4 椋炰功',
+ `notify_attribute` varchar(512) NOT NULL COMMENT '閰嶇疆灞炴��',
+ `description` varchar(256) NOT NULL DEFAULT '' COMMENT '鎻忚堪',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_namespace_id` (`namespace_id`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='鍛婅閫氱煡鎺ユ敹浜�';
+
+CREATE TABLE `sj_retry_dead_letter_0`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `unique_id` varchar(64) NOT NULL COMMENT '鍚岀粍涓媔d鍞竴',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `scene_name` varchar(64) NOT NULL COMMENT '鍦烘櫙鍚嶇О',
+ `idempotent_id` varchar(64) NOT NULL COMMENT '骞傜瓑id',
+ `biz_no` varchar(64) NOT NULL DEFAULT '' COMMENT '涓氬姟缂栧彿',
+ `executor_name` varchar(512) NOT NULL DEFAULT '' COMMENT '鎵ц鍣ㄥ悕绉�',
+ `args_str` text NOT NULL COMMENT '鎵ц鏂规硶鍙傛暟',
+ `ext_attrs` text NOT NULL COMMENT '鎵╁睍瀛楁',
+ `task_type` tinyint(4) NOT NULL DEFAULT 1 COMMENT '浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_namespace_id_group_name_scene_name` (`namespace_id`, `group_name`, `scene_name`),
+ KEY `idx_idempotent_id` (`idempotent_id`),
+ KEY `idx_biz_no` (`biz_no`),
+ KEY `idx_create_dt` (`create_dt`),
+ UNIQUE KEY `uk_namespace_id_group_name_unique_id` (`namespace_id`, `group_name`, `unique_id`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='姝讳俊闃熷垪琛�';
+
+CREATE TABLE `sj_retry_task_0`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `unique_id` varchar(64) NOT NULL COMMENT '鍚岀粍涓媔d鍞竴',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `scene_name` varchar(64) NOT NULL COMMENT '鍦烘櫙鍚嶇О',
+ `idempotent_id` varchar(64) NOT NULL COMMENT '骞傜瓑id',
+ `biz_no` varchar(64) NOT NULL DEFAULT '' COMMENT '涓氬姟缂栧彿',
+ `executor_name` varchar(512) NOT NULL DEFAULT '' COMMENT '鎵ц鍣ㄥ悕绉�',
+ `args_str` text NOT NULL COMMENT '鎵ц鏂规硶鍙傛暟',
+ `ext_attrs` text NOT NULL COMMENT '鎵╁睍瀛楁',
+ `next_trigger_at` datetime NOT NULL COMMENT '涓嬫瑙﹀彂鏃堕棿',
+ `retry_count` int(11) NOT NULL DEFAULT 0 COMMENT '閲嶈瘯娆℃暟',
+ `retry_status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閲嶈瘯鐘舵�� 0銆侀噸璇曚腑 1銆佹垚鍔� 2銆佹渶澶ч噸璇曟鏁�',
+ `task_type` tinyint(4) NOT NULL DEFAULT 1 COMMENT '浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_namespace_id_group_name_scene_name` (`namespace_id`, `group_name`, `scene_name`),
+ KEY `idx_namespace_id_group_name_task_type` (`namespace_id`, `group_name`, `task_type`),
+ KEY `idx_namespace_id_group_name_retry_status` (`namespace_id`, `group_name`, `retry_status`),
+ KEY `idx_idempotent_id` (`idempotent_id`),
+ KEY `idx_biz_no` (`biz_no`),
+ KEY `idx_create_dt` (`create_dt`),
+ UNIQUE KEY `uk_name_unique_id` (`namespace_id`, `group_name`, `unique_id`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='浠诲姟琛�';
+
+CREATE TABLE `sj_retry_task_log`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `unique_id` varchar(64) NOT NULL COMMENT '鍚岀粍涓媔d鍞竴',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `scene_name` varchar(64) NOT NULL COMMENT '鍦烘櫙鍚嶇О',
+ `idempotent_id` varchar(64) NOT NULL COMMENT '骞傜瓑id',
+ `biz_no` varchar(64) NOT NULL DEFAULT '' COMMENT '涓氬姟缂栧彿',
+ `executor_name` varchar(512) NOT NULL DEFAULT '' COMMENT '鎵ц鍣ㄥ悕绉�',
+ `args_str` text NOT NULL COMMENT '鎵ц鏂规硶鍙傛暟',
+ `ext_attrs` text NOT NULL COMMENT '鎵╁睍瀛楁',
+ `retry_status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閲嶈瘯鐘舵�� 0銆侀噸璇曚腑 1銆佹垚鍔� 2銆佹渶澶ф鏁�',
+ `task_type` tinyint(4) NOT NULL DEFAULT 1 COMMENT '浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_group_name_scene_name` (`namespace_id`, `group_name`, `scene_name`),
+ KEY `idx_retry_status` (`retry_status`),
+ KEY `idx_idempotent_id` (`idempotent_id`),
+ KEY `idx_unique_id` (`unique_id`),
+ KEY `idx_biz_no` (`biz_no`),
+ KEY `idx_create_dt` (`create_dt`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='浠诲姟鏃ュ織鍩虹淇℃伅琛�';
+
+CREATE TABLE `sj_retry_task_log_message`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `unique_id` varchar(64) NOT NULL COMMENT '鍚岀粍涓媔d鍞竴',
+ `message` longtext NOT NULL COMMENT '寮傚父淇℃伅',
+ `log_num` int(11) NOT NULL DEFAULT 1 COMMENT '鏃ュ織鏁伴噺',
+ `real_time` bigint(13) NOT NULL DEFAULT 0 COMMENT '涓婃姤鏃堕棿',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_namespace_id_group_name_scene_name` (`namespace_id`, `group_name`, `unique_id`),
+ KEY `idx_create_dt` (`create_dt`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='浠诲姟璋冨害鏃ュ織淇℃伅璁板綍琛�';
+
+CREATE TABLE `sj_retry_scene_config`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `scene_name` varchar(64) NOT NULL COMMENT '鍦烘櫙鍚嶇О',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `scene_status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '缁勭姸鎬� 0銆佹湭鍚敤 1銆佸惎鐢�',
+ `max_retry_count` int(11) NOT NULL DEFAULT 5 COMMENT '鏈�澶ч噸璇曟鏁�',
+ `back_off` tinyint(4) NOT NULL DEFAULT 1 COMMENT '1銆侀粯璁ょ瓑绾� 2銆佸浐瀹氶棿闅旀椂闂� 3銆丆RON 琛ㄨ揪寮�',
+ `trigger_interval` varchar(16) NOT NULL DEFAULT '' COMMENT '闂撮殧鏃堕暱',
+ `deadline_request` bigint(20) unsigned NOT NULL DEFAULT 60000 COMMENT 'Deadline Request 璋冪敤閾捐秴鏃� 鍗曚綅姣',
+ `executor_timeout` int(11) unsigned NOT NULL DEFAULT 5 COMMENT '浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇',
+ `route_key` tinyint(4) NOT NULL DEFAULT 4 COMMENT '璺敱绛栫暐',
+ `description` varchar(256) NOT NULL DEFAULT '' COMMENT '鎻忚堪',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `uk_namespace_id_group_name_scene_name` (`namespace_id`, `group_name`, `scene_name`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='鍦烘櫙閰嶇疆';
+
+CREATE TABLE `sj_server_node`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `host_id` varchar(64) NOT NULL COMMENT '涓绘満id',
+ `host_ip` varchar(64) NOT NULL COMMENT '鏈哄櫒ip',
+ `host_port` int(16) NOT NULL COMMENT '鏈哄櫒绔彛',
+ `expire_at` datetime NOT NULL COMMENT '杩囨湡鏃堕棿',
+ `node_type` tinyint(4) NOT NULL COMMENT '鑺傜偣绫诲瀷 1銆佸鎴风 2銆佹槸鏈嶅姟绔�',
+ `ext_attrs` varchar(256) NULL DEFAULT '' COMMENT '鎵╁睍瀛楁',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_namespace_id_group_name` (`namespace_id`, `group_name`),
+ KEY `idx_expire_at_node_type` (`expire_at`, `node_type`),
+ UNIQUE KEY `uk_host_id_host_ip` (`host_id`, `host_ip`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='鏈嶅姟鍣ㄨ妭鐐�';
+
+CREATE TABLE `sj_distributed_lock`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `name` varchar(64) NOT NULL COMMENT '閿佸悕绉�',
+ `lock_until` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3) COMMENT '閿佸畾鏃堕暱',
+ `locked_at` timestamp(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) COMMENT '閿佸畾鏃堕棿',
+ `locked_by` varchar(255) NOT NULL COMMENT '閿佸畾鑰�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `uk_name` (`name`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='閿佸畾琛�';
+
+CREATE TABLE `sj_system_user`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `username` varchar(64) NOT NULL COMMENT '璐﹀彿',
+ `password` varchar(128) NOT NULL COMMENT '瀵嗙爜',
+ `role` tinyint(4) NOT NULL DEFAULT 0 COMMENT '瑙掕壊锛�1-鏅�氱敤鎴枫��2-绠$悊鍛�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `uk_username` (`username`) USING BTREE
+) ENGINE = InnoDB
+ DEFAULT CHARSET = utf8mb4 COMMENT ='绯荤粺鐢ㄦ埛琛�';
+
+-- pwd: admin
+INSERT INTO `sj_system_user` VALUES (1, 'admin', '465c194afb65670f38322df087f0a9bb225cc257e43eb4ac5a0c98ef5b3173ac', 2, now(), now());
+
+CREATE TABLE `sj_system_user_permission`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `system_user_id` bigint(20) NOT NULL COMMENT '绯荤粺鐢ㄦ埛id',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `uk_namespace_id_group_name_system_user_id` (`namespace_id`, `group_name`, `system_user_id`)
+) ENGINE = InnoDB
+ DEFAULT CHARSET = utf8mb4 COMMENT ='绯荤粺鐢ㄦ埛鏉冮檺琛�';
+
+CREATE TABLE `sj_sequence_alloc`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL DEFAULT '' COMMENT '缁勫悕绉�',
+ `max_id` bigint(20) NOT NULL DEFAULT 1 COMMENT '鏈�澶d',
+ `step` int(11) NOT NULL DEFAULT 100 COMMENT '姝ラ暱',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '鏇存柊鏃堕棿',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `uk_namespace_id_group_name` (`namespace_id`, `group_name`)
+) ENGINE = InnoDB
+ DEFAULT CHARSET = utf8mb4 COMMENT ='鍙锋妯″紡搴忓彿ID鍒嗛厤琛�';
+
+-- 鍒嗗竷寮忚皟搴DL
+CREATE TABLE `sj_job`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `job_name` varchar(64) NOT NULL COMMENT '鍚嶇О',
+ `args_str` text DEFAULT NULL COMMENT '鎵ц鏂规硶鍙傛暟',
+ `args_type` tinyint(4) NOT NULL DEFAULT 1 COMMENT '鍙傛暟绫诲瀷 ',
+ `next_trigger_at` bigint(13) NOT NULL COMMENT '涓嬫瑙﹀彂鏃堕棿',
+ `job_status` tinyint(4) NOT NULL DEFAULT 1 COMMENT '浠诲姟鐘舵�� 0銆佸叧闂��1銆佸紑鍚�',
+ `task_type` tinyint(4) NOT NULL DEFAULT 1 COMMENT '浠诲姟绫诲瀷 1銆侀泦缇� 2銆佸箍鎾� 3銆佸垏鐗�',
+ `route_key` tinyint(4) NOT NULL DEFAULT 4 COMMENT '璺敱绛栫暐',
+ `executor_type` tinyint(4) NOT NULL DEFAULT 1 COMMENT '鎵ц鍣ㄧ被鍨�',
+ `executor_info` varchar(255) DEFAULT NULL COMMENT '鎵ц鍣ㄥ悕绉�',
+ `trigger_type` tinyint(4) NOT NULL COMMENT '瑙﹀彂绫诲瀷 1.CRON 琛ㄨ揪寮� 2. 鍥哄畾鏃堕棿',
+ `trigger_interval` varchar(255) NOT NULL COMMENT '闂撮殧鏃堕暱',
+ `block_strategy` tinyint(4) NOT NULL DEFAULT 1 COMMENT '闃诲绛栫暐 1銆佷涪寮� 2銆佽鐩� 3銆佸苟琛�',
+ `executor_timeout` int(11) NOT NULL DEFAULT 0 COMMENT '浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇',
+ `max_retry_times` int(11) NOT NULL DEFAULT 0 COMMENT '鏈�澶ч噸璇曟鏁�',
+ `parallel_num` int(11) NOT NULL DEFAULT 1 COMMENT '骞惰鏁�',
+ `retry_interval` int(11) NOT NULL DEFAULT 0 COMMENT '閲嶈瘯闂撮殧(s)',
+ `bucket_index` int(11) NOT NULL DEFAULT 0 COMMENT 'bucket',
+ `resident` tinyint(4) NOT NULL DEFAULT 0 COMMENT '鏄惁鏄父椹讳换鍔�',
+ `description` varchar(256) NOT NULL DEFAULT '' COMMENT '鎻忚堪',
+ `ext_attrs` varchar(256) NULL DEFAULT '' COMMENT '鎵╁睍瀛楁',
+ `deleted` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閫昏緫鍒犻櫎 1銆佸垹闄�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_namespace_id_group_name` (`namespace_id`, `group_name`),
+ KEY `idx_job_status_bucket_index` (`job_status`, `bucket_index`),
+ KEY `idx_create_dt` (`create_dt`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='浠诲姟淇℃伅';
+
+INSERT INTO `sj_job` VALUES (1, 'dev', 'ruoyi_group', 'demo-job', null, 1, 1710344035622, 1, 1, 4, 1, 'testJobExecutor', 2, '60', 1, 60, 3, 1, 1, 116, 0, '', '', 0 , now(), now());
+
+CREATE TABLE `sj_job_log_message`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `job_id` bigint(20) NOT NULL COMMENT '浠诲姟淇℃伅id',
+ `task_batch_id` bigint(20) NOT NULL COMMENT '浠诲姟鎵规id',
+ `task_id` bigint(20) NOT NULL COMMENT '璋冨害浠诲姟id',
+ `message` longtext NOT NULL COMMENT '璋冨害淇℃伅',
+ `log_num` int(11) NOT NULL DEFAULT 1 COMMENT '鏃ュ織鏁伴噺',
+ `real_time` bigint(13) NOT NULL DEFAULT 0 COMMENT '涓婃姤鏃堕棿',
+ `ext_attrs` varchar(256) NULL DEFAULT '' COMMENT '鎵╁睍瀛楁',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_task_batch_id_task_id` (`task_batch_id`, `task_id`),
+ KEY `idx_create_dt` (`create_dt`),
+ KEY `idx_namespace_id_group_name` (`namespace_id`, `group_name`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='璋冨害鏃ュ織';
+
+CREATE TABLE `sj_job_task`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `job_id` bigint(20) NOT NULL COMMENT '浠诲姟淇℃伅id',
+ `task_batch_id` bigint(20) NOT NULL COMMENT '璋冨害浠诲姟id',
+ `parent_id` bigint(20) NOT NULL DEFAULT 0 COMMENT '鐖舵墽琛屽櫒id',
+ `task_status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '鎵ц鐨勭姸鎬� 0銆佸け璐� 1銆佹垚鍔�',
+ `retry_count` int(11) NOT NULL DEFAULT 0 COMMENT '閲嶈瘯娆℃暟',
+ `client_info` varchar(128) DEFAULT NULL COMMENT '瀹㈡埛绔湴鍧� clientId#ip:port',
+ `result_message` text NOT NULL COMMENT '鎵ц缁撴灉',
+ `args_str` text DEFAULT NULL COMMENT '鎵ц鏂规硶鍙傛暟',
+ `args_type` tinyint(4) NOT NULL DEFAULT 1 COMMENT '鍙傛暟绫诲瀷 ',
+ `ext_attrs` varchar(256) NULL DEFAULT '' COMMENT '鎵╁睍瀛楁',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_task_batch_id_task_status` (`task_batch_id`, `task_status`),
+ KEY `idx_create_dt` (`create_dt`),
+ KEY `idx_namespace_id_group_name` (`namespace_id`, `group_name`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='浠诲姟瀹炰緥';
+
+CREATE TABLE `sj_job_task_batch`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `job_id` bigint(20) NOT NULL COMMENT '浠诲姟id',
+ `workflow_node_id` bigint(20) NOT NULL DEFAULT 0 COMMENT '宸ヤ綔娴佽妭鐐筰d',
+ `parent_workflow_node_id` bigint(20) NOT NULL DEFAULT 0 COMMENT '宸ヤ綔娴佷换鍔$埗鎵规id',
+ `workflow_task_batch_id` bigint(20) NOT NULL DEFAULT 0 COMMENT '宸ヤ綔娴佷换鍔℃壒娆d',
+ `task_batch_status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '浠诲姟鎵规鐘舵�� 0銆佸け璐� 1銆佹垚鍔�',
+ `operation_reason` tinyint(4) NOT NULL DEFAULT 0 COMMENT '鎿嶄綔鍘熷洜',
+ `execution_at` bigint(13) NOT NULL DEFAULT 0 COMMENT '浠诲姟鎵ц鏃堕棿',
+ `system_task_type` tinyint(4) NOT NULL DEFAULT 3 COMMENT '浠诲姟绫诲瀷 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟',
+ `parent_id` varchar(64) NOT NULL DEFAULT '' COMMENT '鐖惰妭鐐�',
+ `ext_attrs` varchar(256) NULL DEFAULT '' COMMENT '鎵╁睍瀛楁',
+ `deleted` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閫昏緫鍒犻櫎 1銆佸垹闄�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_job_id_task_batch_status` (`job_id`, `task_batch_status`),
+ KEY `idx_create_dt` (`create_dt`),
+ KEY `idx_namespace_id_group_name` (`namespace_id`, `group_name`),
+ KEY `idx_workflow_task_batch_id_workflow_node_id` (`workflow_task_batch_id`, `workflow_node_id`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='浠诲姟鎵规';
+
+CREATE TABLE `sj_job_summary`
+(
+ `id` bigint unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` VARCHAR(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` VARCHAR(64) NOT NULL DEFAULT '' COMMENT '缁勫悕绉�',
+ `business_id` bigint NOT NULL COMMENT '涓氬姟id (job_id鎴杦orkflow_id)',
+ `system_task_type` tinyint(4) NOT NULL DEFAULT 3 COMMENT '浠诲姟绫诲瀷 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟',
+ `trigger_at` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '缁熻鏃堕棿',
+ `success_num` int NOT NULL DEFAULT 0 COMMENT '鎵ц鎴愬姛-鏃ュ織鏁伴噺',
+ `fail_num` int NOT NULL DEFAULT 0 COMMENT '鎵ц澶辫触-鏃ュ織鏁伴噺',
+ `fail_reason` varchar(512) NOT NULL DEFAULT '' COMMENT '澶辫触鍘熷洜',
+ `stop_num` int NOT NULL DEFAULT 0 COMMENT '鎵ц澶辫触-鏃ュ織鏁伴噺',
+ `stop_reason` varchar(512) NOT NULL DEFAULT '' COMMENT '澶辫触鍘熷洜',
+ `cancel_num` int NOT NULL DEFAULT 0 COMMENT '鎵ц澶辫触-鏃ュ織鏁伴噺',
+ `cancel_reason` varchar(512) NOT NULL DEFAULT '' COMMENT '澶辫触鍘熷洜',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_namespace_id_group_name_business_id` (`namespace_id`, `group_name`, business_id),
+ UNIQUE KEY `uk_trigger_at_system_task_type_business_id` (`trigger_at`, `system_task_type`, `business_id`) USING BTREE
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 1
+ DEFAULT CHARSET = utf8mb4 COMMENT ='DashBoard_Job';
+
+CREATE TABLE `sj_retry_summary`
+(
+ `id` bigint unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` VARCHAR(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` VARCHAR(64) NOT NULL DEFAULT '' COMMENT '缁勫悕绉�',
+ `scene_name` VARCHAR(50) NOT NULL DEFAULT '' COMMENT '鍦烘櫙鍚嶇О',
+ `trigger_at` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '缁熻鏃堕棿',
+ `running_num` int NOT NULL DEFAULT 0 COMMENT '閲嶈瘯涓�-鏃ュ織鏁伴噺',
+ `finish_num` int NOT NULL DEFAULT 0 COMMENT '閲嶈瘯瀹屾垚-鏃ュ織鏁伴噺',
+ `max_count_num` int NOT NULL DEFAULT 0 COMMENT '閲嶈瘯鍒拌揪鏈�澶ф鏁�-鏃ュ織鏁伴噺',
+ `suspend_num` int NOT NULL DEFAULT 0 COMMENT '鏆傚仠閲嶈瘯-鏃ュ織鏁伴噺',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_trigger_at` (`trigger_at`),
+ UNIQUE KEY `uk_scene_name_trigger_at` (`namespace_id`, `group_name`, `scene_name`, `trigger_at`) USING BTREE
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 1
+ DEFAULT CHARSET = utf8mb4 COMMENT ='DashBoard_Retry';
+
+CREATE TABLE `sj_workflow`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `workflow_name` varchar(64) NOT NULL COMMENT '宸ヤ綔娴佸悕绉�',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `workflow_status` tinyint(4) NOT NULL DEFAULT 1 COMMENT '宸ヤ綔娴佺姸鎬� 0銆佸叧闂��1銆佸紑鍚�',
+ `trigger_type` tinyint(4) NOT NULL COMMENT '瑙﹀彂绫诲瀷 1.CRON 琛ㄨ揪寮� 2. 鍥哄畾鏃堕棿',
+ `trigger_interval` varchar(255) NOT NULL COMMENT '闂撮殧鏃堕暱',
+ `next_trigger_at` bigint(13) NOT NULL COMMENT '涓嬫瑙﹀彂鏃堕棿',
+ `block_strategy` tinyint(4) NOT NULL DEFAULT 1 COMMENT '闃诲绛栫暐 1銆佷涪寮� 2銆佽鐩� 3銆佸苟琛�',
+ `executor_timeout` int(11) NOT NULL DEFAULT 0 COMMENT '浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇',
+ `description` varchar(256) NOT NULL DEFAULT '' COMMENT '鎻忚堪',
+ `flow_info` text DEFAULT NULL COMMENT '娴佺▼淇℃伅',
+ `bucket_index` int(11) NOT NULL DEFAULT 0 COMMENT 'bucket',
+ `version` int(11) NOT NULL COMMENT '鐗堟湰鍙�',
+ `ext_attrs` varchar(256) NULL DEFAULT '' COMMENT '鎵╁睍瀛楁',
+ `deleted` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閫昏緫鍒犻櫎 1銆佸垹闄�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_create_dt` (`create_dt`),
+ KEY `idx_namespace_id_group_name` (`namespace_id`, `group_name`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='宸ヤ綔娴�';
+
+CREATE TABLE `sj_workflow_node`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `node_name` varchar(64) NOT NULL COMMENT '鑺傜偣鍚嶇О',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `job_id` bigint(20) NOT NULL COMMENT '浠诲姟淇℃伅id',
+ `workflow_id` bigint(20) NOT NULL COMMENT '宸ヤ綔娴両D',
+ `node_type` tinyint(4) NOT NULL DEFAULT 1 COMMENT '1銆佷换鍔¤妭鐐� 2銆佹潯浠惰妭鐐�',
+ `expression_type` tinyint(4) NOT NULL DEFAULT 0 COMMENT '1銆丼pEl銆�2銆丄viator 3銆丵L',
+ `fail_strategy` tinyint(4) NOT NULL DEFAULT 1 COMMENT '澶辫触绛栫暐 1銆佽烦杩� 2銆侀樆濉�',
+ `workflow_node_status` tinyint(4) NOT NULL DEFAULT 1 COMMENT '宸ヤ綔娴佽妭鐐圭姸鎬� 0銆佸叧闂��1銆佸紑鍚�',
+ `priority_level` int(11) NOT NULL DEFAULT 1 COMMENT '浼樺厛绾�',
+ `node_info` text DEFAULT NULL COMMENT '鑺傜偣淇℃伅 ',
+ `version` int(11) NOT NULL COMMENT '鐗堟湰鍙�',
+ `ext_attrs` varchar(256) NULL DEFAULT '' COMMENT '鎵╁睍瀛楁',
+ `deleted` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閫昏緫鍒犻櫎 1銆佸垹闄�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_create_dt` (`create_dt`),
+ KEY `idx_namespace_id_group_name` (`namespace_id`, `group_name`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='宸ヤ綔娴佽妭鐐�';
+
+CREATE TABLE `sj_workflow_task_batch`
+(
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '涓婚敭',
+ `namespace_id` varchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a' COMMENT '鍛藉悕绌洪棿id',
+ `group_name` varchar(64) NOT NULL COMMENT '缁勫悕绉�',
+ `workflow_id` bigint(20) NOT NULL COMMENT '宸ヤ綔娴佷换鍔d',
+ `task_batch_status` tinyint(4) NOT NULL DEFAULT 0 COMMENT '浠诲姟鎵规鐘舵�� 0銆佸け璐� 1銆佹垚鍔�',
+ `operation_reason` tinyint(4) NOT NULL DEFAULT 0 COMMENT '鎿嶄綔鍘熷洜',
+ `flow_info` text DEFAULT NULL COMMENT '娴佺▼淇℃伅',
+ `execution_at` bigint(13) NOT NULL DEFAULT 0 COMMENT '浠诲姟鎵ц鏃堕棿',
+ `ext_attrs` varchar(256) NULL DEFAULT '' COMMENT '鎵╁睍瀛楁',
+ `deleted` tinyint(4) NOT NULL DEFAULT 0 COMMENT '閫昏緫鍒犻櫎 1銆佸垹闄�',
+ `create_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '鍒涘缓鏃堕棿',
+ `update_dt` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '淇敼鏃堕棿',
+ PRIMARY KEY (`id`),
+ KEY `idx_job_id_task_batch_status` (`workflow_id`, `task_batch_status`),
+ KEY `idx_create_dt` (`create_dt`),
+ KEY `idx_namespace_id_group_name` (`namespace_id`, `group_name`)
+) ENGINE = InnoDB
+ AUTO_INCREMENT = 0
+ DEFAULT CHARSET = utf8mb4 COMMENT ='宸ヤ綔娴佹壒娆�';
diff --git a/script/sql/sqlserver/flowable.sql b/script/sql/sqlserver/flowable.sql
new file mode 100644
index 0000000..11ee2be
--- /dev/null
+++ b/script/sql/sqlserver/flowable.sql
@@ -0,0 +1,447 @@
+insert into sys_menu values('11616', '宸ヤ綔娴�' , '0', '6', 'workflow', '', '', '1', '0', 'M', '0', '0', '', 'workflow', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11617', '妯″瀷绠$悊', '11616', '2', 'model', 'workflow/model/index', '', '1', '1', 'C', '0', '0', 'workflow:model:list', 'model', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11618', '鎴戠殑浠诲姟', '0', '7', 'task', '', '', '1', '0', 'M', '0', '0', '', 'my-task', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11619', '鎴戠殑寰呭姙', '11618', '2', 'taskWaiting', 'workflow/task/taskWaiting', '', '1', '1', 'C', '0', '0', '', 'waiting', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11632', '鎴戠殑宸插姙', '11618', '3', 'taskFinish', 'workflow/task/taskFinish', '', '1', '1', 'C', '0', '0', '', 'finish', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11633', '鎴戠殑鎶勯��', '11618', '4', 'taskCopyList', 'workflow/task/taskCopyList', '', '1', '1', 'C', '0', '0', '', 'my-copy', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11620', '娴佺▼瀹氫箟', '11616', '3', 'processDefinition', 'workflow/processDefinition/index', '', '1', '1', 'C', '0', '0', '', 'process-definition', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11621', '娴佺▼瀹炰緥', '11630', '1', 'processInstance', 'workflow/processInstance/index', '', '1', '1', 'C', '0', '0', '', 'tree-table', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11622', '娴佺▼鍒嗙被', '11616', '1', 'category', 'workflow/category/index', '', '1', '0', 'C', '0', '0', 'workflow:category:list', 'category', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11629', '鎴戝彂璧风殑', '11618', '1', 'myDocument', 'workflow/task/myDocument', '', '1', '1', 'C', '0', '0', '', 'guide', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11630', '娴佺▼鐩戞帶', '11616', '4', 'monitor', '', '', '1', '0', 'M', '0', '0', '', 'monitor', 103, 1, getdate(), NULL, NULL, '');
+insert into sys_menu values('11631', '寰呭姙浠诲姟', '11630', '2', 'allTaskWaiting', 'workflow/task/allTaskWaiting', '', '1', '1', 'C', '0', '0', '', 'waiting', 103, 1, getdate(), NULL, NULL, '');
+
+
+-- 娴佺▼鍒嗙被绠$悊鐩稿叧鎸夐挳
+insert into sys_menu values ('11623', '娴佺▼鍒嗙被鏌ヨ', '11622', '1', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:query', '#', 103, 1, getdate(), null, null, '');
+insert into sys_menu values ('11624', '娴佺▼鍒嗙被鏂板', '11622', '2', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:add', '#', 103, 1, getdate(), null, null, '');
+insert into sys_menu values ('11625', '娴佺▼鍒嗙被淇敼', '11622', '3', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:edit', '#', 103, 1, getdate(), null, null, '');
+insert into sys_menu values ('11626', '娴佺▼鍒嗙被鍒犻櫎', '11622', '4', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:remove','#', 103, 1, getdate(), null, null, '');
+insert into sys_menu values ('11627', '娴佺▼鍒嗙被瀵煎嚭', '11622', '5', '#', '', '', 1, 0, 'F', '0', '0', 'workflow:category:export','#', 103, 1, getdate(), null, null, '');
+-- 璇峰亣鍗曚俊鎭�
+create table test_leave
+(
+ id bigint not null
+ primary key,
+ leave_type nvarchar(255) not null,
+ start_date datetime2 not null,
+ end_date datetime2 not null,
+ leave_days int not null,
+ remark nvarchar(255),
+ create_dept bigint,
+ create_by bigint,
+ create_time datetime2,
+ update_by bigint,
+ update_time datetime2,
+ tenant_id nvarchar(20)
+)
+go
+
+exec sp_addextendedproperty 'MS_Description', N'璇峰亣鐢宠琛�', 'SCHEMA', 'dbo', 'TABLE', 'test_leave'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'涓婚敭', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN', 'id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'璇峰亣绫诲瀷', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN',
+ 'leave_type'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'寮�濮嬫椂闂�', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN',
+ 'start_date'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'缁撴潫鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN', 'end_date'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'璇峰亣澶╂暟', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN',
+ 'leave_days'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'璇峰亣鍘熷洜', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN', 'remark'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓閮ㄩ棬', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN',
+ 'create_dept'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鑰�', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN', 'create_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN',
+ 'create_time'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鑰�', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN', 'update_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN',
+ 'update_time'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'绉熸埛缂栧彿', 'SCHEMA', 'dbo', 'TABLE', 'test_leave', 'COLUMN', 'tenant_id'
+go
+
+-- 娴佺▼鍒嗙被淇℃伅琛�
+create table wf_category
+(
+ id bigint not null
+ primary key,
+ category_name nvarchar(255),
+ category_code nvarchar(255)
+ constraint uni_category_code
+ unique,
+ parent_id bigint,
+ sort_num int,
+ tenant_id nvarchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time datetime2,
+ update_by bigint,
+ update_time datetime2
+)
+go
+
+exec sp_addextendedproperty 'MS_Description', N'娴佺▼鍒嗙被', 'SCHEMA', 'dbo', 'TABLE', 'wf_category'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'涓婚敭', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN', 'id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒嗙被鍚嶇О', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN',
+ 'category_name'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒嗙被缂栫爜', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN',
+ 'category_code'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鐖剁骇id', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN', 'parent_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鎺掑簭', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN', 'sort_num'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'绉熸埛缂栧彿', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN',
+ 'tenant_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓閮ㄩ棬', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN',
+ 'create_dept'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN', 'create_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN',
+ 'create_time'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN', 'update_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_category', 'COLUMN',
+ 'update_time'
+go
+
+INSERT INTO wf_category values (1, 'OA', 'OA', 0, 0, '000000', 103, 1, getdate(), 1, getdate());
+
+create table wf_task_back_node
+(
+ id bigint not null primary key,
+ node_id nvarchar(255) not null,
+ node_name nvarchar(255) not null,
+ order_no int not null,
+ instance_id nvarchar(255) not null,
+ task_type nvarchar(255) not null,
+ assignee nvarchar(2000) not null,
+ tenant_id nvarchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time datetime2,
+ update_by bigint,
+ update_time datetime2
+)
+
+go
+exec sp_addextendedproperty 'MS_Description', N'鑺傜偣瀹℃壒璁板綍', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'涓婚敭', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN', 'id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鑺傜偣id', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN',
+ 'node_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鑺傜偣鍚嶇О', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN',
+ 'node_name'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鎺掑簭', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN', 'order_no'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'娴佺▼瀹炰緥id', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN', 'instance_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鑺傜偣绫诲瀷', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN', 'task_type'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'瀹℃壒浜�', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN', 'assignee'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'绉熸埛缂栧彿', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN',
+ 'tenant_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓閮ㄩ棬', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN',
+ 'create_dept'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN', 'create_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN',
+ 'create_time'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN', 'update_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_task_back_node', 'COLUMN',
+ 'update_time'
+go
+
+create table wf_definition_config
+(
+ id bigint not null primary key,
+ table_name nvarchar(255) not null,
+ definition_id nvarchar(255) not null
+ constraint uni_definition_id
+ unique,
+ process_key nvarchar(255) not null,
+ version bigint not null,
+ tenant_id nvarchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time datetime2,
+ update_by bigint,
+ update_time datetime2
+)
+
+go
+exec sp_addextendedproperty 'MS_Description', N'娴佺▼瀹氫箟閰嶇疆', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'涓婚敭', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN', 'id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'琛ㄥ悕', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN',
+ 'table_name'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'娴佺▼瀹氫箟ID', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN',
+ 'definition_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'娴佺▼KEY', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN',
+ 'process_key'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'娴佺▼鐗堟湰', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN',
+ 'version'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'绉熸埛缂栧彿', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN',
+ 'tenant_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓閮ㄩ棬', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN',
+ 'create_dept'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN', 'create_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN',
+ 'create_time'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN', 'update_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_definition_config', 'COLUMN',
+ 'update_time'
+go
+
+create table wf_form_manage
+(
+ id bigint not null primary key,
+ form_name nvarchar(255) not null,
+ form_type nvarchar(255) not null,
+ router nvarchar(255) not null,
+ remark nvarchar(500) null,
+ tenant_id nvarchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time datetime2,
+ update_by bigint,
+ update_time datetime2
+)
+
+go
+exec sp_addextendedproperty 'MS_Description', N'琛ㄥ崟绠$悊', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'涓婚敭', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN', 'id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'琛ㄥ崟鍚嶇О', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN',
+ 'form_name'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'琛ㄥ崟绫诲瀷', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN',
+ 'form_type'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'璺敱鍦板潃/琛ㄥ崟ID', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN',
+ 'router'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'澶囨敞', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN',
+ 'remark'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'绉熸埛缂栧彿', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN',
+ 'tenant_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓閮ㄩ棬', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN',
+ 'create_dept'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN', 'create_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN',
+ 'create_time'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN', 'update_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_form_manage', 'COLUMN',
+ 'update_time'
+go
+
+insert into wf_form_manage(id, form_name, form_type, router, remark, tenant_id, create_dept, create_by, create_time, update_by, update_time) VALUES (1, '璇峰亣鐢宠', 'static', '/demo/leaveEdit/index', NULL, '000000', 103, 1, getdate(), 1, getdate());
+
+create table wf_node_config
+(
+ id bigint not null primary key,
+ form_id bigint,
+ form_type nvarchar(255) ,
+ node_name nvarchar(255) not null,
+ node_id nvarchar(255) not null,
+ definition_id nvarchar(255) not null,
+ apply_user_task nchar default ('0') null,
+ tenant_id nvarchar(20),
+ create_dept bigint,
+ create_by bigint,
+ create_time datetime2,
+ update_by bigint,
+ update_time datetime2
+)
+
+go
+exec sp_addextendedproperty 'MS_Description', N'鑺傜偣閰嶇疆', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'涓婚敭', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN', 'id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'琛ㄥ崟id', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'form_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'琛ㄥ崟绫诲瀷', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'form_type'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鑺傜偣鍚嶇О', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'node_name'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鑺傜偣id', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'node_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'娴佺▼瀹氫箟id', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'definition_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏄惁涓虹敵璇蜂汉鑺傜偣 锛�0鏄� 1鍚︼級', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'apply_user_task'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'绉熸埛缂栧彿', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'tenant_id'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓閮ㄩ棬', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'create_dept'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN', 'create_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鍒涘缓鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'create_time'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鑰�', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN', 'update_by'
+go
+
+exec sp_addextendedproperty 'MS_Description', N'鏇存柊鏃堕棿', 'SCHEMA', 'dbo', 'TABLE', 'wf_node_config', 'COLUMN',
+ 'update_time'
+go
+
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11638, '璇峰亣鐢宠', 5, 1, 'leave', 'workflow/leave/index', 1, 0, 'C', '0', '0', 'demo:leave:list', '#', 103, 1, getdate(), NULL, NULL, '璇峰亣鐢宠鑿滃崟');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11639, '璇峰亣鐢宠鏌ヨ', 11638, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:query', '#', 103, 1, getdate(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11640, '璇峰亣鐢宠鏂板', 11638, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:add', '#', 103, 1, getdate(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11641, '璇峰亣鐢宠淇敼', 11638, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:edit', '#', 103, 1, getdate(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11642, '璇峰亣鐢宠鍒犻櫎', 11638, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:remove', '#', 103, 1, getdate(), NULL, NULL, '');
+INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (11643, '璇峰亣鐢宠瀵煎嚭', 11638, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:leave:export', '#', 103, 1, getdate(), NULL, NULL, '');
+
+INSERT INTO sys_dict_type(dict_id, tenant_id, dict_name, dict_type, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (13, '000000', '涓氬姟鐘舵��', 'wf_business_status', 103, 1, getdate(), NULL, NULL, '涓氬姟鐘舵�佸垪琛�');
+INSERT INTO sys_dict_type(dict_id, tenant_id, dict_name, dict_type, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (14, '000000', '琛ㄥ崟绫诲瀷', 'wf_form_type', 103, 1, getdate(), NULL, NULL, '琛ㄥ崟绫诲瀷鍒楄〃');
+
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (39, '000000', 1, '宸叉挙閿�', 'cancel', 'wf_business_status', '', 'danger', 'N', 103, 1, getdate(), NULL, NULL, '宸叉挙閿�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (40, '000000', 2, '鑽夌', 'draft', 'wf_business_status', '', 'info', 'N', 103, 1, getdate(), NULL, NULL, '鑽夌');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (41, '000000', 3, '寰呭鏍�', 'waiting', 'wf_business_status', '', 'primary', 'N', 103, 1,getdate(), NULL, NULL, '寰呭鏍�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (42, '000000', 4, '宸插畬鎴�', 'finish', 'wf_business_status', '', 'success', 'N', 103, 1, getdate(), NULL, NULL, '宸插畬鎴�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (43, '000000', 5, '宸蹭綔搴�', 'invalid', 'wf_business_status', '', 'danger', 'N', 103, 1, getdate(), NULL, NULL, '宸蹭綔搴�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (44, '000000', 6, '宸查��鍥�', 'back', 'wf_business_status', '', 'danger', 'N', 103, 1, getdate(), NULL, NULL, '宸查��鍥�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (45, '000000', 7, '宸茬粓姝�', 'termination', 'wf_business_status', '', 'danger', 'N', 103, 1,getdate(), NULL, NULL, '宸茬粓姝�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (46, '000000', 1, '鑷畾涔夎〃鍗�', 'static', 'wf_form_type', '', 'success', 'N', 103, 1, getdate(), NULL, NULL, '鑷畾涔夎〃鍗�');
+INSERT INTO sys_dict_data(dict_code, tenant_id, dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (47, '000000', 2, '鍔ㄦ�佽〃鍗�', 'dynamic', 'wf_form_type', '', 'primary', 'N', 103, 1, getdate(), NULL, NULL, '鍔ㄦ�佽〃鍗�');
+
+-- 琛ㄥ崟绠$悊 SQL
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11628, '琛ㄥ崟绠$悊', '11616', '5', 'formManage', 'workflow/formManage/index', 1, 0, 'C', '0', '0', 'workflow:formManage:list', 'tree-table', 103, 1, getdate(), null, null, '琛ㄥ崟绠$悊鑿滃崟');
+
+-- 琛ㄥ崟绠$悊鎸夐挳 SQL
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11644, '琛ㄥ崟绠$悊鏌ヨ', 11628, '1', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:query', '', 103, 1, getdate(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11645, '琛ㄥ崟绠$悊鏂板', 11628, '2', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:add', '', 103, 1, getdate(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11646, '琛ㄥ崟绠$悊淇敼', 11628, '3', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:edit', '', 103, 1, getdate(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11647, '琛ㄥ崟绠$悊鍒犻櫎', 11628, '4', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:remove', '', 103, 1, getdate(), null, null, '');
+
+insert into sys_menu (menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark)
+values(11648, '琛ㄥ崟绠$悊瀵煎嚭', 11628, '5', '#', '', 1, 0, 'F', '0', '0', 'workflow:formManage:export', 'tree-table', 103, 1, getdate(), null, null, '');
diff --git a/script/sql/sqlserver/powerjob.sql b/script/sql/sqlserver/powerjob.sql
deleted file mode 100644
index 1148b2c..0000000
--- a/script/sql/sqlserver/powerjob.sql
+++ /dev/null
@@ -1,517 +0,0 @@
--- ----------------------------
--- Table structure for pj_app_info
--- ----------------------------
-
-CREATE TABLE [pj_app_info] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [app_name] varchar(255) NULL,
- [current_server] varchar(255) NULL,
- [gmt_create] datetime2(7) NULL,
- [gmt_modified] datetime2(7) NULL,
- [password] varchar(255) NULL
-)
-GO
-
-ALTER TABLE [pj_app_info] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Records of [pj_app_info]
--- ----------------------------
-SET IDENTITY_INSERT [pj_app_info] ON
-GO
-
-INSERT INTO [pj_app_info] ([id], [app_name], [current_server], [gmt_create], [gmt_modified], [password]) VALUES (N'1', N'ruoyi-worker', N'192.168.31.100:10010', N'2023-06-13 16:32:59.2630000', N'2023-07-04 17:25:49.7980000', N'123456')
-GO
-
-SET IDENTITY_INSERT [pj_app_info] OFF
-GO
-
-
--- ----------------------------
--- Table structure for pj_container_info
--- ----------------------------
-
-CREATE TABLE [pj_container_info] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [app_id] bigint NULL,
- [container_name] varchar(255) NULL,
- [gmt_create] datetime2(7) NULL,
- [gmt_modified] datetime2(7) NULL,
- [last_deploy_time] datetime2(7) NULL,
- [source_info] varchar(255) NULL,
- [source_type] int NULL,
- [status] int NULL,
- [version] varchar(255) NULL
-)
-GO
-
-ALTER TABLE [pj_container_info] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Table structure for pj_instance_info
--- ----------------------------
-
-CREATE TABLE [pj_instance_info] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [actual_trigger_time] bigint NULL,
- [app_id] bigint NULL,
- [expected_trigger_time] bigint NULL,
- [finished_time] bigint NULL,
- [gmt_create] datetime2(7) NULL,
- [gmt_modified] datetime2(7) NULL,
- [instance_id] bigint NULL,
- [instance_params] varchar(max) NULL,
- [job_id] bigint NULL,
- [job_params] varchar(max) NULL,
- [last_report_time] bigint NULL,
- [result] varchar(max) NULL,
- [running_times] bigint NULL,
- [status] int NULL,
- [task_tracker_address] varchar(255) NULL,
- [type] int NULL,
- [wf_instance_id] bigint NULL
-)
-GO
-
-ALTER TABLE [pj_instance_info] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Table structure for pj_job_info
--- ----------------------------
-
-CREATE TABLE [pj_job_info] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [alarm_config] varchar(255) NULL,
- [app_id] bigint NULL,
- [concurrency] int NULL,
- [designated_workers] varchar(255) NULL,
- [dispatch_strategy] int NULL,
- [execute_type] int NULL,
- [extra] varchar(255) NULL,
- [gmt_create] datetime2(7) NULL,
- [gmt_modified] datetime2(7) NULL,
- [instance_retry_num] int NULL,
- [instance_time_limit] bigint NULL,
- [job_description] varchar(255) NULL,
- [job_name] varchar(255) NULL,
- [job_params] varchar(max) NULL,
- [lifecycle] varchar(255) NULL,
- [log_config] varchar(255) NULL,
- [max_instance_num] int NULL,
- [max_worker_count] int NULL,
- [min_cpu_cores] float(53) NOT NULL,
- [min_disk_space] float(53) NOT NULL,
- [min_memory_space] float(53) NOT NULL,
- [next_trigger_time] bigint NULL,
- [notify_user_ids] varchar(255) NULL,
- [processor_info] varchar(255) NULL,
- [processor_type] int NULL,
- [status] int NULL,
- [tag] varchar(255) NULL,
- [task_retry_num] int NULL,
- [time_expression] varchar(255) NULL,
- [time_expression_type] int NULL
-)
-GO
-
-ALTER TABLE [pj_job_info] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Records of [pj_job_info]
--- ----------------------------
-SET IDENTITY_INSERT [pj_job_info] ON
-GO
-
-INSERT INTO [pj_job_info] ([id], [alarm_config], [app_id], [concurrency], [designated_workers], [dispatch_strategy], [execute_type], [extra], [gmt_create], [gmt_modified], [instance_retry_num], [instance_time_limit], [job_description], [job_name], [job_params], [lifecycle], [log_config], [max_instance_num], [max_worker_count], [min_cpu_cores], [min_disk_space], [min_memory_space], [next_trigger_time], [notify_user_ids], [processor_info], [processor_type], [status], [tag], [task_retry_num], [time_expression], [time_expression_type]) VALUES (N'1', N'{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', N'1', N'5', N'', N'2', N'1', NULL, N'2023-06-02 15:01:27.7170000', N'2023-07-04 17:22:12.3740000', N'1', N'0', N'', N'?????????', NULL, N'{}', N'{"type":1}', N'0', N'0', N'0.000000000000000', N'0.000000000000000', N'0.000000000000000', NULL, NULL, N'org.dromara.job.processors.StandaloneProcessorDemo', N'1', N'2', NULL, N'1', N'30000', N'3')
-GO
-
-INSERT INTO [pj_job_info] ([id], [alarm_config], [app_id], [concurrency], [designated_workers], [dispatch_strategy], [execute_type], [extra], [gmt_create], [gmt_modified], [instance_retry_num], [instance_time_limit], [job_description], [job_name], [job_params], [lifecycle], [log_config], [max_instance_num], [max_worker_count], [min_cpu_cores], [min_disk_space], [min_memory_space], [next_trigger_time], [notify_user_ids], [processor_info], [processor_type], [status], [tag], [task_retry_num], [time_expression], [time_expression_type]) VALUES (N'2', N'{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', N'1', N'5', N'', N'1', N'2', NULL, N'2023-06-02 15:04:45.3420000', N'2023-07-04 17:22:12.8160000', N'0', N'0', NULL, N'???????', NULL, N'{}', N'{"type":1}', N'0', N'0', N'0.000000000000000', N'0.000000000000000', N'0.000000000000000', NULL, NULL, N'org.dromara.job.processors.BroadcastProcessorDemo', N'1', N'2', NULL, N'1', N'30000', N'3')
-GO
-
-INSERT INTO [pj_job_info] ([id], [alarm_config], [app_id], [concurrency], [designated_workers], [dispatch_strategy], [execute_type], [extra], [gmt_create], [gmt_modified], [instance_retry_num], [instance_time_limit], [job_description], [job_name], [job_params], [lifecycle], [log_config], [max_instance_num], [max_worker_count], [min_cpu_cores], [min_disk_space], [min_memory_space], [next_trigger_time], [notify_user_ids], [processor_info], [processor_type], [status], [tag], [task_retry_num], [time_expression], [time_expression_type]) VALUES (N'3', N'{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', N'1', N'5', N'', N'1', N'4', NULL, N'2023-06-02 15:13:23.5190000', N'2023-06-02 16:03:22.4210000', N'0', N'0', NULL, N'Map?????', NULL, N'{}', N'{"type":1}', N'0', N'0', N'0.000000000000000', N'0.000000000000000', N'0.000000000000000', NULL, NULL, N'org.dromara.job.processors.MapProcessorDemo', N'1', N'2', NULL, N'1', N'1000', N'3')
-GO
-
-INSERT INTO [pj_job_info] ([id], [alarm_config], [app_id], [concurrency], [designated_workers], [dispatch_strategy], [execute_type], [extra], [gmt_create], [gmt_modified], [instance_retry_num], [instance_time_limit], [job_description], [job_name], [job_params], [lifecycle], [log_config], [max_instance_num], [max_worker_count], [min_cpu_cores], [min_disk_space], [min_memory_space], [next_trigger_time], [notify_user_ids], [processor_info], [processor_type], [status], [tag], [task_retry_num], [time_expression], [time_expression_type]) VALUES (N'4', N'{"alertThreshold":0,"silenceWindowLen":0,"statisticWindowLen":0}', N'1', N'5', N'', N'1', N'3', NULL, N'2023-06-02 15:45:25.8960000', N'2023-06-02 16:03:23.1250000', N'0', N'0', NULL, N'MapReduce?????', NULL, N'{}', N'{"type":1}', N'0', N'0', N'0.000000000000000', N'0.000000000000000', N'0.000000000000000', NULL, NULL, N'org.dromara.job.processors.MapReduceProcessorDemo', N'1', N'2', NULL, N'1', N'1000', N'3')
-GO
-
-SET IDENTITY_INSERT [pj_job_info] OFF
-GO
-
-
--- ----------------------------
--- Table structure for pj_oms_lock
--- ----------------------------
-
-CREATE TABLE [pj_oms_lock] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [gmt_create] datetime2(7) NULL,
- [gmt_modified] datetime2(7) NULL,
- [lock_name] varchar(255) NULL,
- [max_lock_time] bigint NULL,
- [ownerip] varchar(255) NULL
-)
-GO
-
-ALTER TABLE [pj_oms_lock] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Table structure for pj_server_info
--- ----------------------------
-
-CREATE TABLE [pj_server_info] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [gmt_create] datetime2(7) NULL,
- [gmt_modified] datetime2(7) NULL,
- [ip] varchar(255) NULL
-)
-GO
-
-ALTER TABLE [pj_server_info] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Table structure for pj_user_info
--- ----------------------------
-
-CREATE TABLE [pj_user_info] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [email] varchar(255) NULL,
- [extra] varchar(255) NULL,
- [gmt_create] datetime2(7) NULL,
- [gmt_modified] datetime2(7) NULL,
- [password] varchar(255) NULL,
- [phone] varchar(255) NULL,
- [username] varchar(255) NULL,
- [web_hook] varchar(255) NULL
-)
-GO
-
-ALTER TABLE [pj_user_info] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Table structure for pj_workflow_info
--- ----------------------------
-
-CREATE TABLE [pj_workflow_info] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [app_id] bigint NULL,
- [extra] varchar(255) NULL,
- [gmt_create] datetime2(7) NULL,
- [gmt_modified] datetime2(7) NULL,
- [lifecycle] varchar(255) NULL,
- [max_wf_instance_num] int NULL,
- [next_trigger_time] bigint NULL,
- [notify_user_ids] varchar(255) NULL,
- [pedag] varchar(max) NULL,
- [status] int NULL,
- [time_expression] varchar(255) NULL,
- [time_expression_type] int NULL,
- [wf_description] varchar(255) NULL,
- [wf_name] varchar(255) NULL
-)
-GO
-
-ALTER TABLE [pj_workflow_info] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Table structure for pj_workflow_instance_info
--- ----------------------------
-
-CREATE TABLE [pj_workflow_instance_info] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [actual_trigger_time] bigint NULL,
- [app_id] bigint NULL,
- [dag] varchar(max) NULL,
- [expected_trigger_time] bigint NULL,
- [finished_time] bigint NULL,
- [gmt_create] datetime2(7) NULL,
- [gmt_modified] datetime2(7) NULL,
- [parent_wf_instance_id] bigint NULL,
- [result] varchar(max) NULL,
- [status] int NULL,
- [wf_context] varchar(max) NULL,
- [wf_init_params] varchar(max) NULL,
- [wf_instance_id] bigint NULL,
- [workflow_id] bigint NULL
-)
-GO
-
-ALTER TABLE [pj_workflow_instance_info] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Table structure for pj_workflow_node_info
--- ----------------------------
-
-CREATE TABLE [pj_workflow_node_info] (
- [id] bigint IDENTITY(1,1) NOT NULL,
- [app_id] bigint NOT NULL,
- [enable] bit NOT NULL,
- [extra] varchar(max) NULL,
- [gmt_create] datetime2(7) NOT NULL,
- [gmt_modified] datetime2(7) NOT NULL,
- [job_id] bigint NULL,
- [node_name] varchar(255) NULL,
- [node_params] varchar(max) NULL,
- [skip_when_failed] bit NOT NULL,
- [type] int NULL,
- [workflow_id] bigint NULL
-)
-GO
-
-ALTER TABLE [pj_workflow_node_info] SET (LOCK_ESCALATION = TABLE)
-GO
-
-
--- ----------------------------
--- Uniques structure for table pj_app_info
--- ----------------------------
-ALTER TABLE [pj_app_info] ADD CONSTRAINT [uidx01_app_info] UNIQUE NONCLUSTERED ([app_name] ASC)
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_app_info
--- ----------------------------
-ALTER TABLE [pj_app_info] ADD CONSTRAINT [PK__pj_app_i__3213E83FDD7E2005] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Indexes structure for table pj_container_info
--- ----------------------------
-CREATE NONCLUSTERED INDEX [idx01_container_info]
-ON [pj_container_info] (
- [app_id] ASC
-)
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_container_info
--- ----------------------------
-ALTER TABLE [pj_container_info] ADD CONSTRAINT [PK__pj_conta__3213E83FE1AAA8BE] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Indexes structure for table pj_instance_info
--- ----------------------------
-CREATE NONCLUSTERED INDEX [idx01_instance_info]
-ON [pj_instance_info] (
- [job_id] ASC,
- [status] ASC
-)
-GO
-
-CREATE NONCLUSTERED INDEX [idx02_instance_info]
-ON [pj_instance_info] (
- [app_id] ASC,
- [status] ASC
-)
-GO
-
-CREATE NONCLUSTERED INDEX [idx03_instance_info]
-ON [pj_instance_info] (
- [instance_id] ASC,
- [status] ASC
-)
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_instance_info
--- ----------------------------
-ALTER TABLE [pj_instance_info] ADD CONSTRAINT [PK__pj_insta__3213E83F6F188642] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Indexes structure for table pj_job_info
--- ----------------------------
-CREATE NONCLUSTERED INDEX [idx01_job_info]
-ON [pj_job_info] (
- [app_id] ASC,
- [status] ASC,
- [time_expression_type] ASC,
- [next_trigger_time] ASC
-)
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_job_info
--- ----------------------------
-ALTER TABLE [pj_job_info] ADD CONSTRAINT [PK__pj_job_i__3213E83FBFBCD483] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Uniques structure for table pj_oms_lock
--- ----------------------------
-ALTER TABLE [pj_oms_lock] ADD CONSTRAINT [uidx01_oms_lock] UNIQUE NONCLUSTERED ([lock_name] ASC)
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_oms_lock
--- ----------------------------
-ALTER TABLE [pj_oms_lock] ADD CONSTRAINT [PK__pj_oms_l__3213E83F31F31A08] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Indexes structure for table pj_server_info
--- ----------------------------
-CREATE NONCLUSTERED INDEX [idx01_server_info]
-ON [pj_server_info] (
- [gmt_modified] ASC
-)
-GO
-
-
--- ----------------------------
--- Uniques structure for table pj_server_info
--- ----------------------------
-ALTER TABLE [pj_server_info] ADD CONSTRAINT [uidx01_server_info] UNIQUE NONCLUSTERED ([ip] ASC)
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_server_info
--- ----------------------------
-ALTER TABLE [pj_server_info] ADD CONSTRAINT [PK__pj_serve__3213E83F75246E89] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Indexes structure for table pj_user_info
--- ----------------------------
-CREATE NONCLUSTERED INDEX [uidx01_user_info]
-ON [pj_user_info] (
- [username] ASC
-)
-GO
-
-CREATE NONCLUSTERED INDEX [uidx02_user_info]
-ON [pj_user_info] (
- [email] ASC
-)
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_user_info
--- ----------------------------
-ALTER TABLE [pj_user_info] ADD CONSTRAINT [PK__pj_user___3213E83FB78DE8FD] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Indexes structure for table pj_workflow_info
--- ----------------------------
-CREATE NONCLUSTERED INDEX [idx01_workflow_info]
-ON [pj_workflow_info] (
- [app_id] ASC,
- [status] ASC,
- [time_expression_type] ASC,
- [next_trigger_time] ASC
-)
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_workflow_info
--- ----------------------------
-ALTER TABLE [pj_workflow_info] ADD CONSTRAINT [PK__pj_workf__3213E83F790DC98A] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Indexes structure for table pj_workflow_instance_info
--- ----------------------------
-CREATE NONCLUSTERED INDEX [idx01_wf_instance]
-ON [pj_workflow_instance_info] (
- [workflow_id] ASC,
- [status] ASC,
- [app_id] ASC,
- [expected_trigger_time] ASC
-)
-GO
-
-
--- ----------------------------
--- Uniques structure for table pj_workflow_instance_info
--- ----------------------------
-ALTER TABLE [pj_workflow_instance_info] ADD CONSTRAINT [uidx01_wf_instance] UNIQUE NONCLUSTERED ([wf_instance_id] ASC)
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_workflow_instance_info
--- ----------------------------
-ALTER TABLE [pj_workflow_instance_info] ADD CONSTRAINT [PK__pj_workf__3213E83F5AF8A72D] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
-
--- ----------------------------
--- Indexes structure for table pj_workflow_node_info
--- ----------------------------
-CREATE NONCLUSTERED INDEX [idx01_workflow_node_info]
-ON [pj_workflow_node_info] (
- [workflow_id] ASC,
- [gmt_create] ASC
-)
-GO
-
-
--- ----------------------------
--- Primary Key structure for table pj_workflow_node_info
--- ----------------------------
-ALTER TABLE [pj_workflow_node_info] ADD CONSTRAINT [PK__pj_workf__3213E83FD000EE6D] PRIMARY KEY CLUSTERED ([id])
-WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
-ON [PRIMARY]
-GO
-
diff --git a/script/sql/sqlserver/snail_job_sqlserver.sql b/script/sql/sqlserver/snail_job_sqlserver.sql
new file mode 100644
index 0000000..d6fa1ae
--- /dev/null
+++ b/script/sql/sqlserver/snail_job_sqlserver.sql
@@ -0,0 +1,2697 @@
+/*
+ SnailJob Database Transfer Tool
+ Source Server Type : MySQL
+ Target Server Type : Microsoft SQL Server
+ Date: 2024-05-13 23:03:34
+*/
+
+
+-- sj_namespace
+CREATE TABLE sj_namespace
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ name nvarchar(64) NOT NULL,
+ unique_id nvarchar(64) NOT NULL,
+ description nvarchar(256) NOT NULL DEFAULT '',
+ deleted tinyint NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_namespace_01 ON sj_namespace (name)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_namespace',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍚嶇О',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_namespace',
+ 'COLUMN', N'name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍞竴id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_namespace',
+ 'COLUMN', N'unique_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎻忚堪',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_namespace',
+ 'COLUMN', N'description'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫昏緫鍒犻櫎 1銆佸垹闄�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_namespace',
+ 'COLUMN', N'deleted'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_namespace',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_namespace',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_namespace'
+GO
+
+INSERT INTO sj_namespace(name, unique_id, description, deleted, create_dt, update_dt) VALUES (N'Development', N'dev', N'', 0, getdate(), getdate())
+GO
+INSERT INTO sj_namespace(name, unique_id, description, deleted, create_dt, update_dt) VALUES (N'Production', N'prod', N'', 0, getdate(), getdate())
+GO
+
+-- sj_group_config
+CREATE TABLE sj_group_config
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL DEFAULT '',
+ description nvarchar(256) NOT NULL DEFAULT '',
+ token nvarchar(64) NOT NULL DEFAULT 'SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT',
+ group_status tinyint NOT NULL DEFAULT 0,
+ version int NOT NULL,
+ group_partition int NOT NULL,
+ id_generator_mode tinyint NOT NULL DEFAULT 1,
+ init_scene tinyint NOT NULL DEFAULT 0,
+ bucket_index int NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE UNIQUE INDEX uk_sj_group_config_01 ON sj_group_config (namespace_id, group_name)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勬弿杩�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'description'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'token',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'token'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勭姸鎬� 0銆佹湭鍚敤 1銆佸惎鐢�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'group_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐗堟湰鍙�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'version'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒嗗尯',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'group_partition'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍞竴id鐢熸垚妯″紡 榛樿鍙锋妯″紡',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'id_generator_mode'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏄惁鍒濆鍖栧満鏅� 0:鍚� 1:鏄�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'init_scene'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'bucket',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'bucket_index'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勯厤缃�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_group_config'
+GO
+
+INSERT INTO sj_group_config(namespace_id, group_name, description, token, group_status, version, group_partition, id_generator_mode, init_scene, bucket_index, create_dt, update_dt) VALUES (N'dev', N'ruoyi_group', N'', N'SJ_cKqBTPzCsWA3VyuCfFoccmuIEGXjr5KT', N'1', N'1', N'0', N'1', N'1', N'4', getdate(), getdate())
+GO
+
+-- sj_notify_config
+CREATE TABLE sj_notify_config
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL,
+ business_id nvarchar(64) NOT NULL,
+ system_task_type tinyint NOT NULL DEFAULT 3,
+ notify_status tinyint NOT NULL DEFAULT 0,
+ recipient_ids nvarchar(128) NOT NULL,
+ notify_threshold int NOT NULL DEFAULT 0,
+ notify_scene tinyint NOT NULL DEFAULT 0,
+ rate_limiter_status tinyint NOT NULL DEFAULT 0,
+ rate_limiter_threshold int NOT NULL DEFAULT 0,
+ description nvarchar(256) NOT NULL DEFAULT '',
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_notify_config_01 ON sj_notify_config (namespace_id, group_name, business_id)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓氬姟id ( job_id鎴杦orkflow_id鎴杝cene_name ) ',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'business_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟绫诲瀷 1. 閲嶈瘯浠诲姟 2. 閲嶈瘯鍥炶皟 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'system_task_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫氱煡鐘舵�� 0銆佹湭鍚敤 1銆佸惎鐢�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'notify_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎺ユ敹浜篿d鍒楄〃',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'recipient_ids'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫氱煡闃堝��',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'notify_threshold'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫氱煡鍦烘櫙',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'notify_scene'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'闄愭祦鐘舵�� 0銆佹湭鍚敤 1銆佸惎鐢�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'rate_limiter_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'姣忕闄愭祦闃堝��',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'rate_limiter_threshold'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎻忚堪',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'description'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫氱煡閰嶇疆',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_config'
+GO
+
+-- sj_notify_recipient
+CREATE TABLE sj_notify_recipient
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ recipient_name nvarchar(64) NOT NULL,
+ notify_type tinyint NOT NULL DEFAULT 0,
+ notify_attribute nvarchar(512) NOT NULL,
+ description nvarchar(256) NOT NULL DEFAULT '',
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_notify_recipient_01 ON sj_notify_recipient (namespace_id)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_recipient',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_recipient',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎺ユ敹浜哄悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_recipient',
+ 'COLUMN', N'recipient_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫氱煡绫诲瀷 1銆侀拤閽� 2銆侀偖浠� 3銆佷紒涓氬井淇� 4 椋炰功',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_recipient',
+ 'COLUMN', N'notify_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閰嶇疆灞炴��',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_recipient',
+ 'COLUMN', N'notify_attribute'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎻忚堪',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_recipient',
+ 'COLUMN', N'description'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_recipient',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_recipient',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛婅閫氱煡鎺ユ敹浜�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_notify_recipient'
+GO
+
+-- sj_retry_dead_letter_0
+CREATE TABLE sj_retry_dead_letter_0
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ unique_id nvarchar(64) NOT NULL,
+ group_name nvarchar(64) NOT NULL,
+ scene_name nvarchar(64) NOT NULL,
+ idempotent_id nvarchar(64) NOT NULL,
+ biz_no nvarchar(64) NOT NULL DEFAULT '',
+ executor_name nvarchar(512) NOT NULL DEFAULT '',
+ args_str nvarchar(max) NOT NULL,
+ ext_attrs nvarchar(max) NOT NULL,
+ task_type tinyint NOT NULL DEFAULT 1,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE UNIQUE INDEX uk_sj_retry_dead_letter_0_01 ON sj_retry_dead_letter_0 (namespace_id, group_name, unique_id)
+GO
+
+CREATE INDEX idx_sj_retry_dead_letter_0_01 ON sj_retry_dead_letter_0 (namespace_id, group_name, scene_name)
+GO
+CREATE INDEX idx_sj_retry_dead_letter_0_02 ON sj_retry_dead_letter_0 (idempotent_id)
+GO
+CREATE INDEX idx_sj_retry_dead_letter_0_03 ON sj_retry_dead_letter_0 (biz_no)
+GO
+CREATE INDEX idx_sj_retry_dead_letter_0_04 ON sj_retry_dead_letter_0 (create_dt)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍚岀粍涓媔d鍞竴',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'unique_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍦烘櫙鍚嶇О',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'scene_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'骞傜瓑id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'idempotent_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓氬姟缂栧彿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'biz_no'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鍣ㄥ悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'executor_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鏂规硶鍙傛暟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'args_str'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'task_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'姝讳俊闃熷垪琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_dead_letter_0'
+GO
+
+-- sj_retry_task_0
+CREATE TABLE sj_retry_task_0
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ unique_id nvarchar(64) NOT NULL,
+ group_name nvarchar(64) NOT NULL,
+ scene_name nvarchar(64) NOT NULL,
+ idempotent_id nvarchar(64) NOT NULL,
+ biz_no nvarchar(64) NOT NULL DEFAULT '',
+ executor_name nvarchar(512) NOT NULL DEFAULT '',
+ args_str nvarchar(max) NOT NULL,
+ ext_attrs nvarchar(max) NOT NULL,
+ next_trigger_at datetime2 NOT NULL,
+ retry_count int NOT NULL DEFAULT 0,
+ retry_status tinyint NOT NULL DEFAULT 0,
+ task_type tinyint NOT NULL DEFAULT 1,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE UNIQUE INDEX uk_sj_retry_task_0_01 ON sj_retry_task_0 (namespace_id, group_name, unique_id)
+GO
+
+CREATE INDEX idx_sj_retry_task_0_01 ON sj_retry_task_0 (namespace_id, group_name, scene_name)
+GO
+CREATE INDEX idx_sj_retry_task_0_02 ON sj_retry_task_0 (namespace_id, group_name, task_type)
+GO
+CREATE INDEX idx_sj_retry_task_0_03 ON sj_retry_task_0 (namespace_id, group_name, retry_status)
+GO
+CREATE INDEX idx_sj_retry_task_0_04 ON sj_retry_task_0 (idempotent_id)
+GO
+CREATE INDEX idx_sj_retry_task_0_05 ON sj_retry_task_0 (biz_no)
+GO
+CREATE INDEX idx_sj_retry_task_0_06 ON sj_retry_task_0 (create_dt)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍚岀粍涓媔d鍞竴',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'unique_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍦烘櫙鍚嶇О',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'scene_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'骞傜瓑id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'idempotent_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓氬姟缂栧彿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'biz_no'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鍣ㄥ悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'executor_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鏂规硶鍙傛暟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'args_str'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓嬫瑙﹀彂鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'next_trigger_at'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閲嶈瘯娆℃暟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'retry_count'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閲嶈瘯鐘舵�� 0銆侀噸璇曚腑 1銆佹垚鍔� 2銆佹渶澶ч噸璇曟鏁�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'retry_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'task_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_0'
+GO
+
+-- sj_retry_task_log
+CREATE TABLE sj_retry_task_log
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ unique_id nvarchar(64) NOT NULL,
+ group_name nvarchar(64) NOT NULL,
+ scene_name nvarchar(64) NOT NULL,
+ idempotent_id nvarchar(64) NOT NULL,
+ biz_no nvarchar(64) NOT NULL DEFAULT '',
+ executor_name nvarchar(512) NOT NULL DEFAULT '',
+ args_str nvarchar(max) NOT NULL,
+ ext_attrs nvarchar(max) NOT NULL,
+ retry_status tinyint NOT NULL DEFAULT 0,
+ task_type tinyint NOT NULL DEFAULT 1,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_retry_task_log_01 ON sj_retry_task_log (namespace_id, group_name, scene_name)
+GO
+CREATE INDEX idx_sj_retry_task_log_02 ON sj_retry_task_log (retry_status)
+GO
+CREATE INDEX idx_sj_retry_task_log_03 ON sj_retry_task_log (idempotent_id)
+GO
+CREATE INDEX idx_sj_retry_task_log_04 ON sj_retry_task_log (unique_id)
+GO
+CREATE INDEX idx_sj_retry_task_log_05 ON sj_retry_task_log (biz_no)
+GO
+CREATE INDEX idx_sj_retry_task_log_06 ON sj_retry_task_log (create_dt)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍚岀粍涓媔d鍞竴',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'unique_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍦烘櫙鍚嶇О',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'scene_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'骞傜瓑id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'idempotent_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓氬姟缂栧彿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'biz_no'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鍣ㄥ悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'executor_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鏂规硶鍙傛暟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'args_str'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閲嶈瘯鐘舵�� 0銆侀噸璇曚腑 1銆佹垚鍔� 2銆佹渶澶ф鏁�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'retry_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟绫诲瀷 1銆侀噸璇曟暟鎹� 2銆佸洖璋冩暟鎹�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'task_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鏃ュ織鍩虹淇℃伅琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log'
+GO
+
+-- sj_retry_task_log_message
+CREATE TABLE sj_retry_task_log_message
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL,
+ unique_id nvarchar(64) NOT NULL,
+ message nvarchar(max) NOT NULL,
+ log_num int NOT NULL DEFAULT 1,
+ real_time bigint NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_retry_task_log_message_01 ON sj_retry_task_log_message (namespace_id, group_name, unique_id)
+GO
+CREATE INDEX idx_sj_retry_task_log_message_02 ON sj_retry_task_log_message (create_dt)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log_message',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log_message',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log_message',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍚岀粍涓媔d鍞竴',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log_message',
+ 'COLUMN', N'unique_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'寮傚父淇℃伅',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log_message',
+ 'COLUMN', N'message'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log_message',
+ 'COLUMN', N'log_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婃姤鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log_message',
+ 'COLUMN', N'real_time'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log_message',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟璋冨害鏃ュ織淇℃伅璁板綍琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_task_log_message'
+GO
+
+-- sj_retry_scene_config
+CREATE TABLE sj_retry_scene_config
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ scene_name nvarchar(64) NOT NULL,
+ group_name nvarchar(64) NOT NULL,
+ scene_status tinyint NOT NULL DEFAULT 0,
+ max_retry_count int NOT NULL DEFAULT 5,
+ back_off tinyint NOT NULL DEFAULT 1,
+ trigger_interval nvarchar(16) NOT NULL DEFAULT '',
+ deadline_request bigint NOT NULL DEFAULT 60000,
+ executor_timeout int NOT NULL DEFAULT 5,
+ route_key tinyint NOT NULL DEFAULT 4,
+ description nvarchar(256) NOT NULL DEFAULT '',
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE UNIQUE INDEX uk_sj_retry_scene_config_01 ON sj_retry_scene_config (namespace_id, group_name, scene_name)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍦烘櫙鍚嶇О',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'scene_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勭姸鎬� 0銆佹湭鍚敤 1銆佸惎鐢�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'scene_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏈�澶ч噸璇曟鏁�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'max_retry_count'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'1銆侀粯璁ょ瓑绾� 2銆佸浐瀹氶棿闅旀椂闂� 3銆丆RON 琛ㄨ揪寮�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'back_off'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'闂撮殧鏃堕暱',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'trigger_interval'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'Deadline Request 璋冪敤閾捐秴鏃� 鍗曚綅姣',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'deadline_request'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'executor_timeout'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'璺敱绛栫暐',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'route_key'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎻忚堪',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'description'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍦烘櫙閰嶇疆',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_scene_config'
+GO
+
+-- sj_server_node
+CREATE TABLE sj_server_node
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL,
+ host_id nvarchar(64) NOT NULL,
+ host_ip nvarchar(64) NOT NULL,
+ host_port int NOT NULL,
+ expire_at datetime2 NOT NULL,
+ node_type tinyint NOT NULL,
+ ext_attrs nvarchar(256) NULL DEFAULT '',
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE UNIQUE INDEX uk_sj_server_node_01 ON sj_server_node (host_id, host_ip)
+GO
+
+CREATE INDEX idx_sj_server_node_01 ON sj_server_node (namespace_id, group_name)
+GO
+CREATE INDEX idx_sj_server_node_02 ON sj_server_node (expire_at, node_type)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓绘満id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'host_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏈哄櫒ip',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'host_ip'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏈哄櫒绔彛',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'host_port'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'杩囨湡鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'expire_at'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鑺傜偣绫诲瀷 1銆佸鎴风 2銆佹槸鏈嶅姟绔�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'node_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏈嶅姟鍣ㄨ妭鐐�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_server_node'
+GO
+
+-- sj_distributed_lock
+CREATE TABLE sj_distributed_lock
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ name nvarchar(64) NOT NULL,
+ lock_until datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ locked_at datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ locked_by nvarchar(255) NOT NULL,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_distributed_lock',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閿佸悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_distributed_lock',
+ 'COLUMN', N'name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閿佸畾鏃堕暱',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_distributed_lock',
+ 'COLUMN', N'lock_until'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閿佸畾鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_distributed_lock',
+ 'COLUMN', N'locked_at'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閿佸畾鑰�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_distributed_lock',
+ 'COLUMN', N'locked_by'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_distributed_lock',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_distributed_lock',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閿佸畾琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_distributed_lock'
+GO
+
+-- sj_system_user
+CREATE TABLE sj_system_user
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ username nvarchar(64) NOT NULL,
+ password nvarchar(128) NOT NULL,
+ role tinyint NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'璐﹀彿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user',
+ 'COLUMN', N'username'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'瀵嗙爜',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user',
+ 'COLUMN', N'password'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'瑙掕壊锛�1-鏅�氱敤鎴枫��2-绠$悊鍛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user',
+ 'COLUMN', N'role'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'绯荤粺鐢ㄦ埛琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user'
+GO
+
+-- pwd: admin
+INSERT INTO sj_system_user(username, password, role, create_dt, update_dt) VALUES (N'admin', N'465c194afb65670f38322df087f0a9bb225cc257e43eb4ac5a0c98ef5b3173ac', N'2', getdate(), getdate())
+GO
+
+-- sj_system_user_permission
+CREATE TABLE sj_system_user_permission
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ group_name nvarchar(64) NOT NULL,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ system_user_id bigint NOT NULL,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE UNIQUE INDEX uk_sj_system_user_permission_01 ON sj_system_user_permission (namespace_id, group_name, system_user_id)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user_permission',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user_permission',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user_permission',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'绯荤粺鐢ㄦ埛id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user_permission',
+ 'COLUMN', N'system_user_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user_permission',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user_permission',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'绯荤粺鐢ㄦ埛鏉冮檺琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_system_user_permission'
+GO
+
+-- sj_sequence_alloc
+CREATE TABLE sj_sequence_alloc
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL DEFAULT '',
+ max_id bigint NOT NULL DEFAULT 1,
+ step int NOT NULL DEFAULT 100,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE UNIQUE INDEX uk_sj_sequence_alloc_01 ON sj_sequence_alloc (namespace_id, group_name)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_sequence_alloc',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_sequence_alloc',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_sequence_alloc',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏈�澶d',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_sequence_alloc',
+ 'COLUMN', N'max_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'姝ラ暱',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_sequence_alloc',
+ 'COLUMN', N'step'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏇存柊鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_sequence_alloc',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍙锋妯″紡搴忓彿ID鍒嗛厤琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_sequence_alloc'
+GO
+
+-- sj_job
+CREATE TABLE sj_job
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL,
+ job_name nvarchar(64) NOT NULL,
+ args_str nvarchar(max) NULL DEFAULT NULL,
+ args_type tinyint NOT NULL DEFAULT 1,
+ next_trigger_at bigint NOT NULL,
+ job_status tinyint NOT NULL DEFAULT 1,
+ task_type tinyint NOT NULL DEFAULT 1,
+ route_key tinyint NOT NULL DEFAULT 4,
+ executor_type tinyint NOT NULL DEFAULT 1,
+ executor_info nvarchar(255) NULL DEFAULT NULL,
+ trigger_type tinyint NOT NULL,
+ trigger_interval nvarchar(255) NOT NULL,
+ block_strategy tinyint NOT NULL DEFAULT 1,
+ executor_timeout int NOT NULL DEFAULT 0,
+ max_retry_times int NOT NULL DEFAULT 0,
+ parallel_num int NOT NULL DEFAULT 1,
+ retry_interval int NOT NULL DEFAULT 0,
+ bucket_index int NOT NULL DEFAULT 0,
+ resident tinyint NOT NULL DEFAULT 0,
+ description nvarchar(256) NOT NULL DEFAULT '',
+ ext_attrs nvarchar(256) NULL DEFAULT '',
+ deleted tinyint NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_job_01 ON sj_job (namespace_id, group_name)
+GO
+CREATE INDEX idx_sj_job_02 ON sj_job (job_status, bucket_index)
+GO
+CREATE INDEX idx_sj_job_03 ON sj_job (create_dt)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍚嶇О',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'job_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鏂规硶鍙傛暟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'args_str'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍙傛暟绫诲瀷 ',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'args_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓嬫瑙﹀彂鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'next_trigger_at'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鐘舵�� 0銆佸叧闂��1銆佸紑鍚�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'job_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟绫诲瀷 1銆侀泦缇� 2銆佸箍鎾� 3銆佸垏鐗�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'task_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'璺敱绛栫暐',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'route_key'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鍣ㄧ被鍨�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'executor_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鍣ㄥ悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'executor_info'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'瑙﹀彂绫诲瀷 1.CRON 琛ㄨ揪寮� 2. 鍥哄畾鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'trigger_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'闂撮殧鏃堕暱',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'trigger_interval'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'闃诲绛栫暐 1銆佷涪寮� 2銆佽鐩� 3銆佸苟琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'block_strategy'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'executor_timeout'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏈�澶ч噸璇曟鏁�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'max_retry_times'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'骞惰鏁�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'parallel_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閲嶈瘯闂撮殧 ( s ) ',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'retry_interval'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'bucket',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'bucket_index'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏄惁鏄父椹讳换鍔�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'resident'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎻忚堪',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'description'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫昏緫鍒犻櫎 1銆佸垹闄�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'deleted'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟淇℃伅',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job'
+GO
+
+INSERT INTO sj_job (namespace_id, group_name, job_name, args_str, args_type, next_trigger_at, job_status, task_type, route_key, executor_type, executor_info, trigger_type, trigger_interval, block_strategy,executor_timeout, max_retry_times, parallel_num, retry_interval, bucket_index, resident, description, ext_attrs, deleted, create_dt, update_dt) VALUES (N'dev', N'ruoyi_group', N'demo-job', null, 1, 1710344035622, 1, 1, 4, 1, N'testJobExecutor', 2, N'60', 1, 60, 3, 1, 1, 116, 0, N'', N'', 0, getdate(), getdate())
+GO
+
+-- sj_job_log_message
+CREATE TABLE sj_job_log_message
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL,
+ job_id bigint NOT NULL,
+ task_batch_id bigint NOT NULL,
+ task_id bigint NOT NULL,
+ message nvarchar(max) NOT NULL,
+ log_num int NOT NULL DEFAULT 1,
+ real_time bigint NOT NULL DEFAULT 0,
+ ext_attrs nvarchar(256) NULL DEFAULT '',
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_job_log_message_01 ON sj_job_log_message (task_batch_id, task_id)
+GO
+CREATE INDEX idx_sj_job_log_message_02 ON sj_job_log_message (create_dt)
+GO
+CREATE INDEX idx_sj_job_log_message_03 ON sj_job_log_message (namespace_id, group_name)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟淇℃伅id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'job_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鎵规id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'task_batch_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'璋冨害浠诲姟id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'task_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'璋冨害淇℃伅',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'message'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'log_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婃姤鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'real_time'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'璋冨害鏃ュ織',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_log_message'
+GO
+
+-- sj_job_task
+CREATE TABLE sj_job_task
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL,
+ job_id bigint NOT NULL,
+ task_batch_id bigint NOT NULL,
+ parent_id bigint NOT NULL DEFAULT 0,
+ task_status tinyint NOT NULL DEFAULT 0,
+ retry_count int NOT NULL DEFAULT 0,
+ client_info nvarchar(128) NULL DEFAULT NULL,
+ result_message nvarchar(max) NOT NULL,
+ args_str nvarchar(max) NULL DEFAULT NULL,
+ args_type tinyint NOT NULL DEFAULT 1,
+ ext_attrs nvarchar(256) NULL DEFAULT '',
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_job_task_01 ON sj_job_task (task_batch_id, task_status)
+GO
+CREATE INDEX idx_sj_job_task_02 ON sj_job_task (create_dt)
+GO
+CREATE INDEX idx_sj_job_task_03 ON sj_job_task (namespace_id, group_name)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟淇℃伅id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'job_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'璋冨害浠诲姟id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'task_batch_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐖舵墽琛屽櫒id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'parent_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鐨勭姸鎬� 0銆佸け璐� 1銆佹垚鍔�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'task_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閲嶈瘯娆℃暟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'retry_count'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'瀹㈡埛绔湴鍧� clientId#ip:port',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'client_info'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц缁撴灉',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'result_message'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鏂规硶鍙傛暟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'args_str'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍙傛暟绫诲瀷 ',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'args_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟瀹炰緥',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task'
+GO
+
+-- sj_job_task_batch
+CREATE TABLE sj_job_task_batch
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL,
+ job_id bigint NOT NULL,
+ workflow_node_id bigint NOT NULL DEFAULT 0,
+ parent_workflow_node_id bigint NOT NULL DEFAULT 0,
+ workflow_task_batch_id bigint NOT NULL DEFAULT 0,
+ task_batch_status tinyint NOT NULL DEFAULT 0,
+ operation_reason tinyint NOT NULL DEFAULT 0,
+ execution_at bigint NOT NULL DEFAULT 0,
+ system_task_type tinyint NOT NULL DEFAULT 3,
+ parent_id nvarchar(64) NOT NULL DEFAULT '',
+ ext_attrs nvarchar(256) NULL DEFAULT '',
+ deleted tinyint NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_job_task_batch_01 ON sj_job_task_batch (job_id, task_batch_status)
+GO
+CREATE INDEX idx_sj_job_task_batch_02 ON sj_job_task_batch (create_dt)
+GO
+CREATE INDEX idx_sj_job_task_batch_03 ON sj_job_task_batch (namespace_id, group_name)
+GO
+CREATE INDEX idx_sj_job_task_batch_04 ON sj_job_task_batch (workflow_task_batch_id, workflow_node_id)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'job_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴佽妭鐐筰d',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'workflow_node_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴佷换鍔$埗鎵规id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'parent_workflow_node_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴佷换鍔℃壒娆d',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'workflow_task_batch_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鎵规鐘舵�� 0銆佸け璐� 1銆佹垚鍔�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'task_batch_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎿嶄綔鍘熷洜',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'operation_reason'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鎵ц鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'execution_at'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟绫诲瀷 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'system_task_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐖惰妭鐐�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'parent_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫昏緫鍒犻櫎 1銆佸垹闄�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'deleted'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鎵规',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_task_batch'
+GO
+
+-- sj_job_summary
+CREATE TABLE sj_job_summary
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL DEFAULT '',
+ business_id bigint NOT NULL,
+ system_task_type tinyint NOT NULL DEFAULT 3,
+ trigger_at datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ success_num int NOT NULL DEFAULT 0,
+ fail_num int NOT NULL DEFAULT 0,
+ fail_reason nvarchar(512) NOT NULL DEFAULT '',
+ stop_num int NOT NULL DEFAULT 0,
+ stop_reason nvarchar(512) NOT NULL DEFAULT '',
+ cancel_num int NOT NULL DEFAULT 0,
+ cancel_reason nvarchar(512) NOT NULL DEFAULT '',
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE UNIQUE INDEX uk_sj_job_summary_01 ON sj_job_summary (trigger_at, system_task_type, business_id)
+GO
+
+CREATE INDEX idx_sj_job_summary_01 ON sj_job_summary (namespace_id, group_name, business_id)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓氬姟id ( job_id鎴杦orkflow_id ) ',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'business_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟绫诲瀷 3銆丣OB浠诲姟 4銆乄ORKFLOW浠诲姟',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'system_task_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁熻鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'trigger_at'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц鎴愬姛-鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'success_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц澶辫触-鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'fail_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'澶辫触鍘熷洜',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'fail_reason'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц澶辫触-鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'stop_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'澶辫触鍘熷洜',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'stop_reason'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵ц澶辫触-鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'cancel_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'澶辫触鍘熷洜',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'cancel_reason'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'DashBoard_Job',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_job_summary'
+GO
+
+-- sj_retry_summary
+CREATE TABLE sj_retry_summary
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL DEFAULT '',
+ scene_name nvarchar(50) NOT NULL DEFAULT '',
+ trigger_at datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ running_num int NOT NULL DEFAULT 0,
+ finish_num int NOT NULL DEFAULT 0,
+ max_count_num int NOT NULL DEFAULT 0,
+ suspend_num int NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE UNIQUE INDEX uk_sj_retry_summary_01 ON sj_retry_summary (namespace_id, group_name, scene_name, trigger_at)
+GO
+
+CREATE INDEX idx_sj_retry_summary_01 ON sj_retry_summary (trigger_at)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍦烘櫙鍚嶇О',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'scene_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁熻鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'trigger_at'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閲嶈瘯涓�-鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'running_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閲嶈瘯瀹屾垚-鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'finish_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閲嶈瘯鍒拌揪鏈�澶ф鏁�-鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'max_count_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏆傚仠閲嶈瘯-鏃ュ織鏁伴噺',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'suspend_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'DashBoard_Retry',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_retry_summary'
+GO
+
+-- sj_workflow
+CREATE TABLE sj_workflow
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ workflow_name nvarchar(64) NOT NULL,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL,
+ workflow_status tinyint NOT NULL DEFAULT 1,
+ trigger_type tinyint NOT NULL,
+ trigger_interval nvarchar(255) NOT NULL,
+ next_trigger_at bigint NOT NULL,
+ block_strategy tinyint NOT NULL DEFAULT 1,
+ executor_timeout int NOT NULL DEFAULT 0,
+ description nvarchar(256) NOT NULL DEFAULT '',
+ flow_info nvarchar(max) NULL DEFAULT NULL,
+ bucket_index int NOT NULL DEFAULT 0,
+ version int NOT NULL,
+ ext_attrs nvarchar(256) NULL DEFAULT '',
+ deleted tinyint NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_workflow_01 ON sj_workflow (create_dt)
+GO
+CREATE INDEX idx_sj_workflow_02 ON sj_workflow (namespace_id, group_name)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴佸悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'workflow_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴佺姸鎬� 0銆佸叧闂��1銆佸紑鍚�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'workflow_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'瑙﹀彂绫诲瀷 1.CRON 琛ㄨ揪寮� 2. 鍥哄畾鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'trigger_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'闂撮殧鏃堕暱',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'trigger_interval'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓嬫瑙﹀彂鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'next_trigger_at'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'闃诲绛栫暐 1銆佷涪寮� 2銆佽鐩� 3銆佸苟琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'block_strategy'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鎵ц瓒呮椂鏃堕棿锛屽崟浣嶇',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'executor_timeout'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎻忚堪',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'description'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'娴佺▼淇℃伅',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'flow_info'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'bucket',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'bucket_index'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐗堟湰鍙�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'version'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫昏緫鍒犻櫎 1銆佸垹闄�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'deleted'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow'
+GO
+
+-- sj_workflow_node
+CREATE TABLE sj_workflow_node
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ node_name nvarchar(64) NOT NULL,
+ group_name nvarchar(64) NOT NULL,
+ job_id bigint NOT NULL,
+ workflow_id bigint NOT NULL,
+ node_type tinyint NOT NULL DEFAULT 1,
+ expression_type tinyint NOT NULL DEFAULT 0,
+ fail_strategy tinyint NOT NULL DEFAULT 1,
+ workflow_node_status tinyint NOT NULL DEFAULT 1,
+ priority_level int NOT NULL DEFAULT 1,
+ node_info nvarchar(max) NULL DEFAULT NULL,
+ version int NOT NULL,
+ ext_attrs nvarchar(256) NULL DEFAULT '',
+ deleted tinyint NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_workflow_node_01 ON sj_workflow_node (create_dt)
+GO
+CREATE INDEX idx_sj_workflow_node_02 ON sj_workflow_node (namespace_id, group_name)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鑺傜偣鍚嶇О',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'node_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟淇℃伅id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'job_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴両D',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'workflow_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'1銆佷换鍔¤妭鐐� 2銆佹潯浠惰妭鐐�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'node_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'1銆丼pEl銆�2銆丄viator 3銆丵L',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'expression_type'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'澶辫触绛栫暐 1銆佽烦杩� 2銆侀樆濉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'fail_strategy'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴佽妭鐐圭姸鎬� 0銆佸叧闂��1銆佸紑鍚�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'workflow_node_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浼樺厛绾�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'priority_level'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鑺傜偣淇℃伅 ',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'node_info'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐗堟湰鍙�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'version'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫昏緫鍒犻櫎 1銆佸垹闄�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'deleted'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴佽妭鐐�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_node'
+GO
+
+-- sj_workflow_task_batch
+CREATE TABLE sj_workflow_task_batch
+(
+ id bigint NOT NULL PRIMARY KEY IDENTITY,
+ namespace_id nvarchar(64) NOT NULL DEFAULT '764d604ec6fc45f68cd92514c40e9e1a',
+ group_name nvarchar(64) NOT NULL,
+ workflow_id bigint NOT NULL,
+ task_batch_status tinyint NOT NULL DEFAULT 0,
+ operation_reason tinyint NOT NULL DEFAULT 0,
+ flow_info nvarchar(max) NULL DEFAULT NULL,
+ execution_at bigint NOT NULL DEFAULT 0,
+ ext_attrs nvarchar(256) NULL DEFAULT '',
+ deleted tinyint NOT NULL DEFAULT 0,
+ create_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ update_dt datetime2 NOT NULL DEFAULT CURRENT_TIMESTAMP
+)
+GO
+
+CREATE INDEX idx_sj_workflow_task_batch_01 ON sj_workflow_task_batch (workflow_id, task_batch_status)
+GO
+CREATE INDEX idx_sj_workflow_task_batch_02 ON sj_workflow_task_batch (create_dt)
+GO
+CREATE INDEX idx_sj_workflow_task_batch_03 ON sj_workflow_task_batch (namespace_id, group_name)
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍛藉悕绌洪棿id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'namespace_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'缁勫悕绉�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'group_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴佷换鍔d',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'workflow_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鎵规鐘舵�� 0銆佸け璐� 1銆佹垚鍔�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'task_batch_status'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎿嶄綔鍘熷洜',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'operation_reason'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'娴佺▼淇℃伅',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'flow_info'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'浠诲姟鎵ц鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'execution_at'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎵╁睍瀛楁',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'ext_attrs'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閫昏緫鍒犻櫎 1銆佸垹闄�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'deleted'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'create_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'淇敼鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch',
+ 'COLUMN', N'update_dt'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宸ヤ綔娴佹壒娆�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sj_workflow_task_batch'
+GO
+
diff --git a/script/sql/sqlserver/sqlserver_ry_vue_5.X.sql b/script/sql/sqlserver/sqlserver_ry_vue_5.X.sql
index a27ac5d..00f0771 100644
--- a/script/sql/sqlserver/sqlserver_ry_vue_5.X.sql
+++ b/script/sql/sqlserver/sqlserver_ry_vue_5.X.sql
@@ -17,7 +17,7 @@
union_id nvarchar(255) NULL,
scope nvarchar(255) NULL,
token_type nvarchar(255) NULL,
- id_token nvarchar(255) NULL,
+ id_token nvarchar(2000) NULL,
mac_algorithm nvarchar(255) NULL,
mac_key nvarchar(255) NULL,
code nvarchar(255) NULL,
@@ -926,7 +926,8 @@
tenant_id nvarchar(20) DEFAULT ('000000') NULL,
parent_id bigint DEFAULT ((0)) NULL,
ancestors nvarchar(500)DEFAULT '' NULL,
- dept_name nvarchar(30) DEFAULT '' NULL,
+ dept_name nvarchar(30) NULL,
+ dept_category nvarchar(100) DEFAULT '' NULL,
order_num int DEFAULT ((0)) NULL,
leader bigint NULL,
phone nvarchar(11) NULL,
@@ -974,6 +975,12 @@
'SCHEMA', N'dbo',
'TABLE', N'sys_dept',
'COLUMN', N'dept_name'
+GO
+EXEC sys.sp_addextendedproperty
+ 'MS_Description', N'閮ㄩ棬绫诲埆缂栫爜' ,
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_dept',
+ 'COLUMN', N'dept_category'
GO
EXEC sys.sp_addextendedproperty
'MS_Description', N'鏄剧ず椤哄簭' ,
@@ -1047,25 +1054,25 @@
'TABLE', N'sys_dept'
GO
-INSERT sys_dept VALUES (100, N'000000', 0, N'0', N'XXX绉戞妧', 0, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (100, N'000000', 0, N'0', N'XXX绉戞妧', NULL, 0, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
-INSERT sys_dept VALUES (101, N'000000', 100, N'0,100', N'娣卞湷鎬诲叕鍙�', 1, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (101, N'000000', 100, N'0,100', N'娣卞湷鎬诲叕鍙�', NULL, 1, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
-INSERT sys_dept VALUES (102, N'000000', 100, N'0,100', N'闀挎矙鍒嗗叕鍙�', 2, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (102, N'000000', 100, N'0,100', N'闀挎矙鍒嗗叕鍙�', NULL, 2, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
-INSERT sys_dept VALUES (103, N'000000', 101, N'0,100,101', N'鐮斿彂閮ㄩ棬', 1, 1, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (103, N'000000', 101, N'0,100,101', N'鐮斿彂閮ㄩ棬', NULL, 1, 1, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
-INSERT sys_dept VALUES (104, N'000000', 101, N'0,100,101', N'甯傚満閮ㄩ棬', 2, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (104, N'000000', 101, N'0,100,101', N'甯傚満閮ㄩ棬', NULL, 2, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
-INSERT sys_dept VALUES (105, N'000000', 101, N'0,100,101', N'娴嬭瘯閮ㄩ棬', 3, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (105, N'000000', 101, N'0,100,101', N'娴嬭瘯閮ㄩ棬', NULL, 3, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
-INSERT sys_dept VALUES (106, N'000000', 101, N'0,100,101', N'璐㈠姟閮ㄩ棬', 4, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (106, N'000000', 101, N'0,100,101', N'璐㈠姟閮ㄩ棬', NULL, 4, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
-INSERT sys_dept VALUES (107, N'000000', 101, N'0,100,101', N'杩愮淮閮ㄩ棬', 5, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (107, N'000000', 101, N'0,100,101', N'杩愮淮閮ㄩ棬', NULL, 5, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
-INSERT sys_dept VALUES (108, N'000000', 102, N'0,100,102', N'甯傚満閮ㄩ棬', 1, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (108, N'000000', 102, N'0,100,102', N'甯傚満閮ㄩ棬', NULL, 1, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
-INSERT sys_dept VALUES (109, N'000000', 102, N'0,100,102', N'璐㈠姟閮ㄩ棬', 2, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
+INSERT sys_dept VALUES (109, N'000000', 102, N'0,100,102', N'璐㈠姟閮ㄩ棬', NULL, 2, NULL, N'15888888888', N'xxx@qq.com', N'0', N'0', 103, 1, getdate(), NULL, NULL)
GO
CREATE TABLE sys_dict_data
@@ -1647,6 +1654,8 @@
GO
INSERT sys_menu VALUES (4, N'PLUS瀹樼綉', 0, 5, N'https://gitee.com/dromara/RuoYi-Vue-Plus', null, N'', 0, 0, N'M', N'0', N'0', N'', N'guide', 103, 1, getdate(), null, null, N'RuoYi-Vue-Plus瀹樼綉鍦板潃');
GO
+INSERT sys_menu VALUES (5, N'娴嬭瘯鑿滃崟', 0, 5, N'demo', NULL, N'', 1, 0, N'M', N'0', N'0', NULL, N'star', 103, 1, getdate(), NULL, NULL, N'');
+GO
INSERT sys_menu VALUES (100, N'鐢ㄦ埛绠$悊', 1, 1, N'user', N'system/user/index', N'', 1, 0, N'C', N'0', N'0', N'system:user:list', N'user', 103, 1, getdate(), NULL, NULL, N'鐢ㄦ埛绠$悊鑿滃崟')
GO
INSERT sys_menu VALUES (101, N'瑙掕壊绠$悊', 1, 2, N'role', N'system/role/index', N'', 1, 0, N'C', N'0', N'0', N'system:role:list', N'peoples', 103, 1, getdate(), NULL, NULL, N'瑙掕壊绠$悊鑿滃崟')
@@ -1683,7 +1692,7 @@
GO
INSERT sys_menu VALUES (118, N'鏂囦欢绠$悊', 1, 10, N'oss', N'system/oss/index', N'', 1, 0, N'C', '0', N'0', N'system:oss:list', N'upload', 103, 1, getdate(), NULL, NULL, N'鏂囦欢绠$悊鑿滃崟');
GO
-INSERT sys_menu VALUES (120, N'浠诲姟璋冨害涓績', 2, 5, N'powerjob', N'monitor/powerjob/index', N'', 1, 0, N'C', N'0', N'0', N'monitor:powerjob:list', N'job', 103, 1, getdate(), NULL, NULL, N'PowerJob鎺у埗鍙拌彍鍗�');
+INSERT sys_menu VALUES (120, N'浠诲姟璋冨害涓績', 2, 5, N'snailjob', N'monitor/snailjob/index', N'', 1, 0, N'C', N'0', N'0', N'monitor:snailjob:list', N'job', 103, 1, getdate(), NULL, NULL, N'SnailJob鎺у埗鍙拌彍鍗�');
GO
INSERT sys_menu VALUES (500, N'鎿嶄綔鏃ュ織', 108, 1, N'operlog', N'monitor/operlog/index', N'', 1, 0, N'C', N'0', N'0', N'monitor:operlog:list', N'form', 103, 1, getdate(), NULL, NULL, N'鎿嶄綔鏃ュ織鑿滃崟')
GO
@@ -1848,6 +1857,32 @@
INSERT sys_menu VALUES (1064, N'瀹㈡埛绔鐞嗗垹闄�', 123, 4, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'system:client:remove', N'#', 103, 1, getdate(), NULL, NULL, N'');
GO
INSERT sys_menu VALUES (1065, N'瀹㈡埛绔鐞嗗鍑�', 123, 5, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'system:client:export', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+-- 娴嬭瘯鑿滃崟
+INSERT sys_menu VALUES (1500, N'娴嬭瘯鍗曡〃', 5, 1, N'demo', N'demo/demo/index', N'', 1, 0, N'C', N'0', N'0', N'demo:demo:list', N'#', 103, 1, getdate(), NULL, NULL, N'娴嬭瘯鍗曡〃鑿滃崟');
+GO
+INSERT sys_menu VALUES (1501, N'娴嬭瘯鍗曡〃鏌ヨ', 1500, 1, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:query', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+INSERT sys_menu VALUES (1502, N'娴嬭瘯鍗曡〃鏂板', 1500, 2, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:add', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+INSERT sys_menu VALUES (1503, N'娴嬭瘯鍗曡〃淇敼', 1500, 3, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:edit', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+INSERT sys_menu VALUES (1504, N'娴嬭瘯鍗曡〃鍒犻櫎', 1500, 4, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:remove', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+INSERT sys_menu VALUES (1505, N'娴嬭瘯鍗曡〃瀵煎嚭', 1500, 5, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:export', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+
+INSERT sys_menu VALUES (1506, N'娴嬭瘯鏍戣〃', 5, 1, N'tree', N'demo/tree/index', N'', 1, 0, N'C', N'0', N'0', N'demo:tree:list', N'#', 103, 1, getdate(), NULL, NULL, N'娴嬭瘯鏍戣〃鑿滃崟');
+GO
+INSERT sys_menu VALUES (1507, N'娴嬭瘯鏍戣〃鏌ヨ', 1506, 1, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:query', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+INSERT sys_menu VALUES (1508, N'娴嬭瘯鏍戣〃鏂板', 1506, 2, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:add', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+INSERT sys_menu VALUES (1509, N'娴嬭瘯鏍戣〃淇敼', 1506, 3, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:edit', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+INSERT sys_menu VALUES (1510, N'娴嬭瘯鏍戣〃鍒犻櫎', 1506, 4, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:remove', N'#', 103, 1, getdate(), NULL, NULL, N'');
+GO
+INSERT sys_menu VALUES (1511, N'娴嬭瘯鏍戣〃瀵煎嚭', 1506, 5, N'#', N'', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:export', N'#', 103, 1, getdate(), NULL, NULL, N'');
GO
CREATE TABLE sys_notice
@@ -2107,7 +2142,9 @@
(
post_id bigint NOT NULL,
tenant_id nvarchar(20) DEFAULT ('000000') NULL,
+ dept_id bigint NOT NULL,
post_code nvarchar(64) NOT NULL,
+ post_category nvarchar(100) NULL,
post_name nvarchar(50) NOT NULL,
post_sort int NOT NULL,
status nchar(1) NOT NULL,
@@ -2137,10 +2174,22 @@
'COLUMN', N'tenant_id'
GO
EXEC sys.sp_addextendedproperty
+ 'MS_Description', N'閮ㄩ棬id' ,
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_post',
+ 'COLUMN', N'dept_id'
+GO
+EXEC sys.sp_addextendedproperty
'MS_Description', N'宀椾綅缂栫爜' ,
'SCHEMA', N'dbo',
'TABLE', N'sys_post',
'COLUMN', N'post_code'
+GO
+EXEC sys.sp_addextendedproperty
+ 'MS_Description', N'宀椾綅绫诲埆缂栫爜' ,
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_post',
+ 'COLUMN', N'post_category'
GO
EXEC sys.sp_addextendedproperty
'MS_Description', N'宀椾綅鍚嶇О' ,
@@ -2202,13 +2251,13 @@
'TABLE', N'sys_post'
GO
-INSERT sys_post VALUES (1, N'000000', N'ceo', N'钁d簨闀�', 1, N'0', 103, 1, getdate(), NULL, NULL, N'')
+INSERT sys_post VALUES (1, N'000000', 103, N'ceo', NULL, N'钁d簨闀�', 1, N'0', 103, 1, getdate(), NULL, NULL, N'')
GO
-INSERT sys_post VALUES (2, N'000000', N'se', N'椤圭洰缁忕悊', 2, N'0', 103, 1, getdate(), NULL, NULL, N'')
+INSERT sys_post VALUES (2, N'000000', 100, N'se', NULL, N'椤圭洰缁忕悊', 2, N'0', 103, 1, getdate(), NULL, NULL, N'')
GO
-INSERT sys_post VALUES (3, N'000000', N'hr', N'浜哄姏璧勬簮', 3, N'0', 103, 1, getdate(), NULL, NULL, N'')
+INSERT sys_post VALUES (3, N'000000', 100, N'hr', NULL, N'浜哄姏璧勬簮', 3, N'0', 103, 1, getdate(), NULL, NULL, N'')
GO
-INSERT sys_post VALUES (4, N'000000', N'user', N'鏅�氬憳宸�', 4, N'0', 103, 1, getdate(), NULL, NULL, N'')
+INSERT sys_post VALUES (4, N'000000', 100, N'user', NULL, N'鏅�氬憳宸�', 4, N'0', 103, 1, getdate(), NULL, NULL, N'')
GO
CREATE TABLE sys_role
@@ -2340,7 +2389,9 @@
INSERT sys_role VALUES (1, N'000000', N'瓒呯骇绠$悊鍛�', N'superadmin', 1, N'1', 1, 1, N'0', N'0', 103, 1, getdate(), NULL, NULL, N'瓒呯骇绠$悊鍛�')
GO
-INSERT sys_role VALUES (2, N'000000', N'鏅�氳鑹�', N'common', 2, N'2', 1, 1, N'0', N'0', 103, 1, getdate(), NULL, NULL, N'鏅�氳鑹�')
+INSERT sys_role VALUES (3, N'000000', N'鏈儴闂ㄥ強浠ヤ笅', N'test1', 3, N'4', 1, 1, N'0', N'0', 103, 1, getdate(), NULL, NULL, N'');
+GO
+INSERT sys_role VALUES (4, N'000000', N'浠呮湰浜�', N'test2', 4, N'5', 1, 1, N'0', N'0', 103, 1, getdate(), NULL, NULL, N'');
GO
CREATE TABLE sys_role_dept
@@ -2372,13 +2423,6 @@
'TABLE', N'sys_role_dept'
GO
-INSERT sys_role_dept VALUES (2, 100)
-GO
-INSERT sys_role_dept VALUES (2, 101)
-GO
-INSERT sys_role_dept VALUES (2, 105)
-GO
-
CREATE TABLE sys_role_menu
(
role_id bigint NOT NULL,
@@ -2408,179 +2452,174 @@
'TABLE', N'sys_role_menu'
GO
-INSERT sys_role_menu VALUES (2, 1)
+-- ----------------------------
+-- 鍒濆鍖�-瑙掕壊鍜岃彍鍗曞叧鑱旇〃鏁版嵁
+-- ----------------------------
+INSERT sys_role_menu VALUES (3, 1);
GO
-INSERT sys_role_menu VALUES (2, 2)
+INSERT sys_role_menu VALUES (3, 5);
GO
-INSERT sys_role_menu VALUES (2, 3)
+INSERT sys_role_menu VALUES (3, 100);
GO
-INSERT sys_role_menu VALUES (2, 100)
+INSERT sys_role_menu VALUES (3, 101);
GO
-INSERT sys_role_menu VALUES (2, 101)
+INSERT sys_role_menu VALUES (3, 102);
GO
-INSERT sys_role_menu VALUES (2, 102)
+INSERT sys_role_menu VALUES (3, 103);
GO
-INSERT sys_role_menu VALUES (2, 103)
+INSERT sys_role_menu VALUES (3, 104);
GO
-INSERT sys_role_menu VALUES (2, 104)
+INSERT sys_role_menu VALUES (3, 105);
GO
-INSERT sys_role_menu VALUES (2, 105)
+INSERT sys_role_menu VALUES (3, 106);
GO
-INSERT sys_role_menu VALUES (2, 106)
+INSERT sys_role_menu VALUES (3, 107);
GO
-INSERT sys_role_menu VALUES (2, 107)
+INSERT sys_role_menu VALUES (3, 108);
GO
-INSERT sys_role_menu VALUES (2, 108)
+INSERT sys_role_menu VALUES (3, 500);
GO
-INSERT sys_role_menu VALUES (2, 109)
+INSERT sys_role_menu VALUES (3, 501);
GO
-INSERT sys_role_menu VALUES (2, 110)
+INSERT sys_role_menu VALUES (3, 1001);
GO
-INSERT sys_role_menu VALUES (2, 111)
+INSERT sys_role_menu VALUES (3, 1002);
GO
-INSERT sys_role_menu VALUES (2, 112)
+INSERT sys_role_menu VALUES (3, 1003);
GO
-INSERT sys_role_menu VALUES (2, 113)
+INSERT sys_role_menu VALUES (3, 1004);
GO
-INSERT sys_role_menu VALUES (2, 114)
+INSERT sys_role_menu VALUES (3, 1005);
GO
-INSERT sys_role_menu VALUES (2, 115)
+INSERT sys_role_menu VALUES (3, 1006);
GO
-INSERT sys_role_menu VALUES (2, 116)
+INSERT sys_role_menu VALUES (3, 1007);
GO
-INSERT sys_role_menu VALUES (2, 500)
+INSERT sys_role_menu VALUES (3, 1008);
GO
-INSERT sys_role_menu VALUES (2, 501)
+INSERT sys_role_menu VALUES (3, 1009);
GO
-INSERT sys_role_menu VALUES (2, 1001)
+INSERT sys_role_menu VALUES (3, 1010);
GO
-INSERT sys_role_menu VALUES (2, 1002)
+INSERT sys_role_menu VALUES (3, 1011);
GO
-INSERT sys_role_menu VALUES (2, 1003)
+INSERT sys_role_menu VALUES (3, 1012);
GO
-INSERT sys_role_menu VALUES (2, 1004)
+INSERT sys_role_menu VALUES (3, 1013);
GO
-INSERT sys_role_menu VALUES (2, 1005)
+INSERT sys_role_menu VALUES (3, 1014);
GO
-INSERT sys_role_menu VALUES (2, 1006)
+INSERT sys_role_menu VALUES (3, 1015);
GO
-INSERT sys_role_menu VALUES (2, 1007)
+INSERT sys_role_menu VALUES (3, 1016);
GO
-INSERT sys_role_menu VALUES (2, 1008)
+INSERT sys_role_menu VALUES (3, 1017);
GO
-INSERT sys_role_menu VALUES (2, 1009)
+INSERT sys_role_menu VALUES (3, 1018);
GO
-INSERT sys_role_menu VALUES (2, 1010)
+INSERT sys_role_menu VALUES (3, 1019);
GO
-INSERT sys_role_menu VALUES (2, 1011)
+INSERT sys_role_menu VALUES (3, 1020);
GO
-INSERT sys_role_menu VALUES (2, 1012)
+INSERT sys_role_menu VALUES (3, 1021);
GO
-INSERT sys_role_menu VALUES (2, 1013)
+INSERT sys_role_menu VALUES (3, 1022);
GO
-INSERT sys_role_menu VALUES (2, 1014)
+INSERT sys_role_menu VALUES (3, 1023);
GO
-INSERT sys_role_menu VALUES (2, 1015)
+INSERT sys_role_menu VALUES (3, 1024);
GO
-INSERT sys_role_menu VALUES (2, 1016)
+INSERT sys_role_menu VALUES (3, 1025);
GO
-INSERT sys_role_menu VALUES (2, 1017)
+INSERT sys_role_menu VALUES (3, 1026);
GO
-INSERT sys_role_menu VALUES (2, 1018)
+INSERT sys_role_menu VALUES (3, 1027);
GO
-INSERT sys_role_menu VALUES (2, 1019)
+INSERT sys_role_menu VALUES (3, 1028);
GO
-INSERT sys_role_menu VALUES (2, 1020)
+INSERT sys_role_menu VALUES (3, 1029);
GO
-INSERT sys_role_menu VALUES (2, 1021)
-GO
-INSERT sys_role_menu VALUES (2, 1022)
-GO
-INSERT sys_role_menu VALUES (2, 1023)
-GO
-INSERT sys_role_menu VALUES (2, 1024)
-GO
-INSERT sys_role_menu VALUES (2, 1025)
+INSERT sys_role_menu VALUES (3, 1030);
GO
-INSERT sys_role_menu VALUES (2, 1026)
+INSERT sys_role_menu VALUES (3, 1031);
GO
-INSERT sys_role_menu VALUES (2, 1027)
+INSERT sys_role_menu VALUES (3, 1032);
GO
-INSERT sys_role_menu VALUES (2, 1028)
+INSERT sys_role_menu VALUES (3, 1033);
GO
-INSERT sys_role_menu VALUES (2, 1029)
+INSERT sys_role_menu VALUES (3, 1034);
GO
-INSERT sys_role_menu VALUES (2, 1030)
+INSERT sys_role_menu VALUES (3, 1035);
GO
-INSERT sys_role_menu VALUES (2, 1031)
+INSERT sys_role_menu VALUES (3, 1036);
GO
-INSERT sys_role_menu VALUES (2, 1032)
+INSERT sys_role_menu VALUES (3, 1037);
GO
-INSERT sys_role_menu VALUES (2, 1033)
+INSERT sys_role_menu VALUES (3, 1038);
GO
-INSERT sys_role_menu VALUES (2, 1034)
+INSERT sys_role_menu VALUES (3, 1039);
GO
-INSERT sys_role_menu VALUES (2, 1035)
+INSERT sys_role_menu VALUES (3, 1040);
GO
-INSERT sys_role_menu VALUES (2, 1036)
+INSERT sys_role_menu VALUES (3, 1041);
GO
-INSERT sys_role_menu VALUES (2, 1037)
+INSERT sys_role_menu VALUES (3, 1042);
GO
-INSERT sys_role_menu VALUES (2, 1038)
+INSERT sys_role_menu VALUES (3, 1043);
GO
-INSERT sys_role_menu VALUES (2, 1039)
+INSERT sys_role_menu VALUES (3, 1044);
GO
-INSERT sys_role_menu VALUES (2, 1040)
+INSERT sys_role_menu VALUES (3, 1045);
GO
-INSERT sys_role_menu VALUES (2, 1041)
+INSERT sys_role_menu VALUES (3, 1500);
GO
-INSERT sys_role_menu VALUES (2, 1042)
+INSERT sys_role_menu VALUES (3, 1501);
GO
-INSERT sys_role_menu VALUES (2, 1043)
+INSERT sys_role_menu VALUES (3, 1502);
GO
-INSERT sys_role_menu VALUES (2, 1044)
+INSERT sys_role_menu VALUES (3, 1503);
GO
-INSERT sys_role_menu VALUES (2, 1045)
+INSERT sys_role_menu VALUES (3, 1504);
GO
-INSERT sys_role_menu VALUES (2, 1046)
+INSERT sys_role_menu VALUES (3, 1505);
GO
-INSERT sys_role_menu VALUES (2, 1047)
+INSERT sys_role_menu VALUES (3, 1506);
GO
-INSERT sys_role_menu VALUES (2, 1048)
+INSERT sys_role_menu VALUES (3, 1507);
GO
-INSERT sys_role_menu VALUES (2, 1049)
+INSERT sys_role_menu VALUES (3, 1508);
GO
-INSERT sys_role_menu VALUES (2, 1050)
+INSERT sys_role_menu VALUES (3, 1509);
GO
-INSERT sys_role_menu VALUES (2, 1051)
+INSERT sys_role_menu VALUES (3, 1510);
GO
-INSERT sys_role_menu VALUES (2, 1052)
+INSERT sys_role_menu VALUES (3, 1511);
GO
-INSERT sys_role_menu VALUES (2, 1053)
+INSERT sys_role_menu VALUES (4, 5);
GO
-INSERT sys_role_menu VALUES (2, 1054)
+INSERT sys_role_menu VALUES (4, 1500);
GO
-INSERT sys_role_menu VALUES (2, 1055)
+INSERT sys_role_menu VALUES (4, 1501);
GO
-INSERT sys_role_menu VALUES (2, 1056)
+INSERT sys_role_menu VALUES (4, 1502);
GO
-INSERT sys_role_menu VALUES (2, 1057)
+INSERT sys_role_menu VALUES (4, 1503);
GO
-INSERT sys_role_menu VALUES (2, 1058)
+INSERT sys_role_menu VALUES (4, 1504);
GO
-INSERT sys_role_menu VALUES (2, 1059)
+INSERT sys_role_menu VALUES (4, 1505);
GO
-INSERT sys_role_menu VALUES (2, 1060)
+INSERT sys_role_menu VALUES (4, 1506);
GO
-INSERT sys_role_menu VALUES (2, 1061)
+INSERT sys_role_menu VALUES (4, 1507);
GO
-INSERT sys_role_menu VALUES (2, 1062)
+INSERT sys_role_menu VALUES (4, 1508);
GO
-INSERT sys_role_menu VALUES (2, 1063)
+INSERT sys_role_menu VALUES (4, 1509);
GO
-INSERT sys_role_menu VALUES (2, 1064)
+INSERT sys_role_menu VALUES (4, 1510);
GO
-INSERT sys_role_menu VALUES (2, 1065)
+INSERT sys_role_menu VALUES (4, 1511);
GO
CREATE TABLE sys_user
@@ -2747,7 +2786,9 @@
INSERT sys_user VALUES (1, N'000000', 103, N'admin', N'鐤媯鐨勭嫯瀛怢i', N'sys_user', N'crazyLionLi@163.com', N'15888888888', N'1', NULL, N'$2a$10$7JB720yubVSZvUI0rEqK/.VqGOZTH.ulu33dHOiBE8ByOhJIrdAu2', N'0', N'0', N'127.0.0.1', getdate(), 103, 1, getdate(), NULL, NULL, N'绠$悊鍛�')
GO
-INSERT sys_user VALUES (2, N'000000', 105, N'lionli', N'鐤媯鐨勭嫯瀛怢i', N'sys_user', N'crazyLionLi@qq.com', N'15666666666', N'1', NULL, N'$2a$10$7JB720yubVSZvUI0rEqK/.VqGOZTH.ulu33dHOiBE8ByOhJIrdAu2', N'0', N'0', N'127.0.0.1', getdate(), 103, 1, getdate(), NULL, NULL, N'娴嬭瘯鍛�')
+INSERT sys_user VALUES (3, N'000000', 108, N'test', N'鏈儴闂ㄥ強浠ヤ笅 瀵嗙爜666666', N'sys_user', N'', N'', N'0', NULL, N'$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', N'0', N'0', N'127.0.0.1', getdate(), 103, 1, getdate(), 3, getdate(), NULL);
+GO
+INSERT sys_user VALUES (4, N'000000', 102, N'test1', N'浠呮湰浜� 瀵嗙爜666666', N'sys_user', N'', N'', N'0', NULL, N'$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', N'0', N'0', N'127.0.0.1', getdate(), 103, 1, getdate(), 4, getdate(), NULL);
GO
CREATE TABLE sys_user_post
@@ -2781,8 +2822,6 @@
INSERT sys_user_post VALUES (1, 1)
GO
-INSERT sys_user_post VALUES (2, 2)
-GO
CREATE TABLE sys_user_role
(
@@ -2815,7 +2854,9 @@
INSERT sys_user_role VALUES (1, 1)
GO
-INSERT sys_user_role VALUES (2, 2)
+INSERT sys_user_role VALUES (3, 3);
+GO
+INSERT sys_user_role VALUES (4, 4);
GO
CREATE TABLE sys_oss
@@ -2947,7 +2988,7 @@
GO
EXEC sp_addextendedproperty
- 'MS_Description', N'涓诲缓',
+ 'MS_Description', N'涓婚敭',
'SCHEMA', N'dbo',
'TABLE', N'sys_oss_config',
'COLUMN', N'oss_config_id'
@@ -3109,102 +3150,402 @@
GO
EXEC sp_addextendedproperty
-'MS_Description', N'涓诲缓',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'id'
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'id'
GO
EXEC sys.sp_addextendedproperty
-'MS_Description', N'瀹㈡埛绔痠d' ,
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'client_id'
+ 'MS_Description', N'瀹㈡埛绔痠d' ,
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'client_id'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'瀹㈡埛绔痥ey',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'client_key'
+ 'MS_Description', N'瀹㈡埛绔痥ey',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'client_key'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'瀹㈡埛绔閽�',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'client_secret'
+ 'MS_Description', N'瀹㈡埛绔閽�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'client_secret'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'鎺堟潈绫诲瀷',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'grant_type'
+ 'MS_Description', N'鎺堟潈绫诲瀷',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'grant_type'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'璁惧绫诲瀷',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'device_type'
+ 'MS_Description', N'璁惧绫诲瀷',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'device_type'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'token娲昏穬瓒呮椂鏃堕棿',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'active_timeout'
+ 'MS_Description', N'token娲昏穬瓒呮椂鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'active_timeout'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'token鍥哄畾瓒呮椂',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'timeout'
+ 'MS_Description', N'token鍥哄畾瓒呮椂',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'timeout'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'鐘舵�侊紙0姝e父 1鍋滅敤锛�',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'status'
+ 'MS_Description', N'鐘舵�侊紙0姝e父 1鍋滅敤锛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'status'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'鍒犻櫎鏍囧織锛�0浠h〃瀛樺湪 2浠h〃鍒犻櫎锛�',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'del_flag'
+ 'MS_Description', N'鍒犻櫎鏍囧織锛�0浠h〃瀛樺湪 2浠h〃鍒犻櫎锛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'del_flag'
GO
EXEC sys.sp_addextendedproperty
-'MS_Description', N'鍒涘缓閮ㄩ棬' ,
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'create_dept'
+ 'MS_Description', N'鍒涘缓閮ㄩ棬' ,
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'create_dept'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'鍒涘缓鑰�',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'create_by'
+ 'MS_Description', N'鍒涘缓鑰�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'create_by'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'鍒涘缓鏃堕棿',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'create_time'
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'create_time'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'鏇存柊鑰�',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'update_by'
+ 'MS_Description', N'鏇存柊鑰�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'update_by'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'鏇存柊鏃堕棿',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client',
-'COLUMN', N'update_time'
+ 'MS_Description', N'鏇存柊鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client',
+ 'COLUMN', N'update_time'
GO
EXEC sp_addextendedproperty
-'MS_Description', N'绯荤粺鎺堟潈琛�',
-'SCHEMA', N'dbo',
-'TABLE', N'sys_client'
+ 'MS_Description', N'绯荤粺鎺堟潈琛�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_client'
GO
INSERT INTO sys_client VALUES (N'1', N'e5cd7e4891bf95d1d19206ce24a7b32e', N'pc', N'pc123', N'password,social', N'pc', 1800, 604800, N'0', N'0', 103, 1, getdate(), 1, getdate())
GO
INSERT INTO sys_client VALUES (N'2', N'428a8310cd442757ae699df5d894f051', N'app', N'app123', N'password,sms,social', N'android', 1800, 604800, N'0', N'0', 103, 1, getdate(), 1, getdate())
GO
+
+CREATE TABLE test_demo
+(
+ id bigint NOT NULL,
+ tenant_id nvarchar(20) DEFAULT ('000000') NULL,
+ dept_id bigint NULL,
+ user_id bigint NULL,
+ order_num int DEFAULT ((0)) NULL,
+ test_key nvarchar(255) NULL,
+ value nvarchar(255) NULL,
+ version int DEFAULT ((0)) NULL,
+ create_dept bigint NULL,
+ create_time datetime2(0) NULL,
+ create_by bigint NULL,
+ update_time datetime2(0) NULL,
+ update_by bigint NULL,
+ del_flag int DEFAULT ((0)) NULL,
+ CONSTRAINT PK__test_dem__3213E83F176051C8 PRIMARY KEY CLUSTERED (id)
+ WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
+ ON [PRIMARY]
+)
+ON [PRIMARY]
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'绉熸埛id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'tenant_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閮ㄩ棬id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'dept_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐢ㄦ埛id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'user_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鎺掑簭鍙�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'order_num'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'key閿�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'test_key'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍊�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'value'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐗堟湰',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'version'
+GO
+
+EXEC sys.sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓閮ㄩ棬' ,
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'create_dept'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'create_time'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓浜�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'create_by'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏇存柊鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'update_time'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏇存柊浜�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'update_by'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒犻櫎鏍囧織',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo',
+ 'COLUMN', N'del_flag'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'娴嬭瘯鍗曡〃',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_demo'
+GO
+
+CREATE TABLE test_tree
+(
+ id bigint NOT NULL,
+ tenant_id nvarchar(20) DEFAULT ('000000') NULL,
+ parent_id bigint DEFAULT ((0)) NULL,
+ dept_id bigint NULL,
+ user_id bigint NULL,
+ tree_name nvarchar(255) NULL,
+ version int DEFAULT ((0)) NULL,
+ create_dept bigint NULL,
+ create_time datetime2(0) NULL,
+ create_by bigint NULL,
+ update_time datetime2(0) NULL,
+ update_by bigint NULL,
+ del_flag int DEFAULT ((0)) NULL,
+ CONSTRAINT PK__test_tre__3213E83FC75A1B63 PRIMARY KEY CLUSTERED (id)
+ WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
+ ON [PRIMARY]
+)
+ON [PRIMARY]
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'涓婚敭',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'绉熸埛id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'tenant_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐖秈d',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'parent_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閮ㄩ棬id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'dept_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐢ㄦ埛id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'user_id'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍊�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'tree_name'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鐗堟湰',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'version'
+GO
+
+EXEC sys.sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓閮ㄩ棬' ,
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'create_dept'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'create_time'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒涘缓浜�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'create_by'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏇存柊鏃堕棿',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'update_time'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鏇存柊浜�',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'update_by'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'鍒犻櫎鏍囧織',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree',
+ 'COLUMN', N'del_flag'
+GO
+
+EXEC sp_addextendedproperty
+ 'MS_Description', N'娴嬭瘯鏍戣〃',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'test_tree'
+GO
+
+INSERT test_demo VALUES (1, N'000000', 102, 4, 1, N'娴嬭瘯鏁版嵁鏉冮檺', N'娴嬭瘯', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (2, N'000000', 102, 3, 2, N'瀛愯妭鐐�1', N'111', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (3, N'000000', 102, 3, 3, N'瀛愯妭鐐�2', N'222', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (4, N'000000', 108, 4, 4, N'娴嬭瘯鏁版嵁', N'demo', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (5, N'000000', 108, 3, 13, N'瀛愯妭鐐�11', N'1111', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (6, N'000000', 108, 3, 12, N'瀛愯妭鐐�22', N'2222', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (7, N'000000', 108, 3, 11, N'瀛愯妭鐐�33', N'3333', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (8, N'000000', 108, 3, 10, N'瀛愯妭鐐�44', N'4444', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (9, N'000000', 108, 3, 9, N'瀛愯妭鐐�55', N'5555', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (10, N'000000', 108, 3, 8, N'瀛愯妭鐐�66', N'6666', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (11, N'000000', 108, 3, 7, N'瀛愯妭鐐�77', N'7777', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (12, N'000000', 108, 3, 6, N'瀛愯妭鐐�88', N'8888', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_demo VALUES (13, N'000000', 108, 3, 5, N'瀛愯妭鐐�99', N'9999', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+
+INSERT test_tree VALUES (1, N'000000', 0, 102, 4, N'娴嬭瘯鏁版嵁鏉冮檺', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (2, N'000000', 1, 102, 3, N'瀛愯妭鐐�1', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (3, N'000000', 2, 102, 3, N'瀛愯妭鐐�2', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (4, N'000000', 0, 108, 4, N'娴嬭瘯鏍�1', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (5, N'000000', 4, 108, 3, N'瀛愯妭鐐�11', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (6, N'000000', 4, 108, 3, N'瀛愯妭鐐�22', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (7, N'000000', 4, 108, 3, N'瀛愯妭鐐�33', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (8, N'000000', 5, 108, 3, N'瀛愯妭鐐�44', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (9, N'000000', 6, 108, 3, N'瀛愯妭鐐�55', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (10, N'000000', 7, 108, 3, N'瀛愯妭鐐�66', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (11, N'000000', 7, 108, 3, N'瀛愯妭鐐�77', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (12, N'000000', 10, 108, 3, N'瀛愯妭鐐�88', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
+INSERT test_tree VALUES (13, N'000000', 10, 108, 3, N'瀛愯妭鐐�99', 0, 103, getdate(), 1, NULL, NULL, 0);
+GO
diff --git a/script/sql/sqlserver/sqlserver_test.sql b/script/sql/sqlserver/sqlserver_test.sql
deleted file mode 100644
index 87628bd..0000000
--- a/script/sql/sqlserver/sqlserver_test.sql
+++ /dev/null
@@ -1,510 +0,0 @@
-CREATE TABLE test_demo
-(
- id bigint NOT NULL,
- tenant_id nvarchar(20) DEFAULT ('000000') NULL,
- dept_id bigint NULL,
- user_id bigint NULL,
- order_num int DEFAULT ((0)) NULL,
- test_key nvarchar(255) NULL,
- value nvarchar(255) NULL,
- version int DEFAULT ((0)) NULL,
- create_dept bigint NULL,
- create_time datetime2(0) NULL,
- create_by bigint NULL,
- update_time datetime2(0) NULL,
- update_by bigint NULL,
- del_flag int DEFAULT ((0)) NULL,
- CONSTRAINT PK__test_dem__3213E83F176051C8 PRIMARY KEY CLUSTERED (id)
- WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
- ON [PRIMARY]
-)
-ON [PRIMARY]
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'涓婚敭',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'id'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'绉熸埛id',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'tenant_id'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'閮ㄩ棬id',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'dept_id'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鐢ㄦ埛id',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'user_id'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鎺掑簭鍙�',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'order_num'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'key閿�',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'test_key'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鍊�',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'value'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鐗堟湰',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'version'
-GO
-
-EXEC sys.sp_addextendedproperty
- 'MS_Description', N'鍒涘缓閮ㄩ棬' ,
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'create_dept'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鍒涘缓鏃堕棿',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'create_time'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鍒涘缓浜�',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'create_by'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鏇存柊鏃堕棿',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'update_time'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鏇存柊浜�',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'update_by'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鍒犻櫎鏍囧織',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo',
- 'COLUMN', N'del_flag'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'娴嬭瘯鍗曡〃',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_demo'
-GO
-
-CREATE TABLE test_tree
-(
- id bigint NOT NULL,
- tenant_id nvarchar(20) DEFAULT ('000000') NULL,
- parent_id bigint DEFAULT ((0)) NULL,
- dept_id bigint NULL,
- user_id bigint NULL,
- tree_name nvarchar(255) NULL,
- version int DEFAULT ((0)) NULL,
- create_dept bigint NULL,
- create_time datetime2(0) NULL,
- create_by bigint NULL,
- update_time datetime2(0) NULL,
- update_by bigint NULL,
- del_flag int DEFAULT ((0)) NULL,
- CONSTRAINT PK__test_tre__3213E83FC75A1B63 PRIMARY KEY CLUSTERED (id)
- WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
- ON [PRIMARY]
-)
-ON [PRIMARY]
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'涓婚敭',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'id'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'绉熸埛id',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'tenant_id'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鐖秈d',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'parent_id'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'閮ㄩ棬id',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'dept_id'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鐢ㄦ埛id',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'user_id'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鍊�',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'tree_name'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鐗堟湰',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'version'
-GO
-
-EXEC sys.sp_addextendedproperty
- 'MS_Description', N'鍒涘缓閮ㄩ棬' ,
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'create_dept'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鍒涘缓鏃堕棿',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'create_time'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鍒涘缓浜�',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'create_by'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鏇存柊鏃堕棿',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'update_time'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鏇存柊浜�',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'update_by'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'鍒犻櫎鏍囧織',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree',
- 'COLUMN', N'del_flag'
-GO
-
-EXEC sp_addextendedproperty
- 'MS_Description', N'娴嬭瘯鏍戣〃',
- 'SCHEMA', N'dbo',
- 'TABLE', N'test_tree'
-GO
-
-INSERT sys_user VALUES (3, N'000000', 108, N'test', N'鏈儴闂ㄥ強浠ヤ笅 瀵嗙爜666666', N'sys_user', N'', N'', N'0', NULL, N'$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', N'0', N'0', N'127.0.0.1', getdate(), 103, 1, getdate(), 3, getdate(), NULL);
-GO
-INSERT sys_user VALUES (4, N'000000', 102, N'test1', N'浠呮湰浜� 瀵嗙爜666666', N'sys_user', N'', N'', N'0', NULL, N'$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', N'0', N'0', N'127.0.0.1', getdate(), 103, 1, getdate(), 4, getdate(), NULL);
-GO
-
-INSERT sys_menu VALUES (5, N'娴嬭瘯鑿滃崟', 0, 5, N'demo', NULL, 1, 0, N'M', N'0', N'0', NULL, N'star', 103, 1, getdate(), NULL, NULL, N'');
-GO
-
-INSERT sys_menu VALUES (1500, N'娴嬭瘯鍗曡〃', 5, 1, N'demo', N'demo/demo/index', 1, 0, N'C', N'0', N'0', N'demo:demo:list', N'#', 103, 1, getdate(), NULL, NULL, N'娴嬭瘯鍗曡〃鑿滃崟');
-GO
-INSERT sys_menu VALUES (1501, N'娴嬭瘯鍗曡〃鏌ヨ', 1500, 1, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:query', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-INSERT sys_menu VALUES (1502, N'娴嬭瘯鍗曡〃鏂板', 1500, 2, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:add', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-INSERT sys_menu VALUES (1503, N'娴嬭瘯鍗曡〃淇敼', 1500, 3, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:edit', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-INSERT sys_menu VALUES (1504, N'娴嬭瘯鍗曡〃鍒犻櫎', 1500, 4, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:remove', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-INSERT sys_menu VALUES (1505, N'娴嬭瘯鍗曡〃瀵煎嚭', 1500, 5, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:demo:export', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-
-INSERT sys_menu VALUES (1506, N'娴嬭瘯鏍戣〃', 5, 1, N'tree', N'demo/tree/index', 1, 0, N'C', N'0', N'0', N'demo:tree:list', N'#', 103, 1, getdate(), NULL, NULL, N'娴嬭瘯鏍戣〃鑿滃崟');
-GO
-INSERT sys_menu VALUES (1507, N'娴嬭瘯鏍戣〃鏌ヨ', 1506, 1, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:query', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-INSERT sys_menu VALUES (1508, N'娴嬭瘯鏍戣〃鏂板', 1506, 2, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:add', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-INSERT sys_menu VALUES (1509, N'娴嬭瘯鏍戣〃淇敼', 1506, 3, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:edit', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-INSERT sys_menu VALUES (1510, N'娴嬭瘯鏍戣〃鍒犻櫎', 1506, 4, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:remove', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-INSERT sys_menu VALUES (1511, N'娴嬭瘯鏍戣〃瀵煎嚭', 1506, 5, N'#', N'', 1, 0, N'F', N'0', N'0', N'demo:tree:export', N'#', 103, 1, getdate(), NULL, NULL, N'');
-GO
-
-INSERT sys_role VALUES (3, N'000000', N'鏈儴闂ㄥ強浠ヤ笅', N'test1', 3, N'4', 1, 1, N'0', N'0', 103, 1, getdate(), 1, NULL, NULL);
-GO
-INSERT sys_role VALUES (4, N'000000', N'浠呮湰浜�', N'test2', 4, N'5', 1, 1, N'0', N'0', 103, 1, getdate(), 1, NULL, NULL);
-GO
-
-INSERT sys_role_menu VALUES (3, 1);
-GO
-INSERT sys_role_menu VALUES (3, 5);
-GO
-INSERT sys_role_menu VALUES (3, 100);
-GO
-INSERT sys_role_menu VALUES (3, 101);
-GO
-INSERT sys_role_menu VALUES (3, 102);
-GO
-INSERT sys_role_menu VALUES (3, 103);
-GO
-INSERT sys_role_menu VALUES (3, 104);
-GO
-INSERT sys_role_menu VALUES (3, 105);
-GO
-INSERT sys_role_menu VALUES (3, 106);
-GO
-INSERT sys_role_menu VALUES (3, 107);
-GO
-INSERT sys_role_menu VALUES (3, 108);
-GO
-INSERT sys_role_menu VALUES (3, 500);
-GO
-INSERT sys_role_menu VALUES (3, 501);
-GO
-INSERT sys_role_menu VALUES (3, 1001);
-GO
-INSERT sys_role_menu VALUES (3, 1002);
-GO
-INSERT sys_role_menu VALUES (3, 1003);
-GO
-INSERT sys_role_menu VALUES (3, 1004);
-GO
-INSERT sys_role_menu VALUES (3, 1005);
-GO
-INSERT sys_role_menu VALUES (3, 1006);
-GO
-INSERT sys_role_menu VALUES (3, 1007);
-GO
-INSERT sys_role_menu VALUES (3, 1008);
-GO
-INSERT sys_role_menu VALUES (3, 1009);
-GO
-INSERT sys_role_menu VALUES (3, 1010);
-GO
-INSERT sys_role_menu VALUES (3, 1011);
-GO
-INSERT sys_role_menu VALUES (3, 1012);
-GO
-INSERT sys_role_menu VALUES (3, 1013);
-GO
-INSERT sys_role_menu VALUES (3, 1014);
-GO
-INSERT sys_role_menu VALUES (3, 1015);
-GO
-INSERT sys_role_menu VALUES (3, 1016);
-GO
-INSERT sys_role_menu VALUES (3, 1017);
-GO
-INSERT sys_role_menu VALUES (3, 1018);
-GO
-INSERT sys_role_menu VALUES (3, 1019);
-GO
-INSERT sys_role_menu VALUES (3, 1020);
-GO
-INSERT sys_role_menu VALUES (3, 1021);
-GO
-INSERT sys_role_menu VALUES (3, 1022);
-GO
-INSERT sys_role_menu VALUES (3, 1023);
-GO
-INSERT sys_role_menu VALUES (3, 1024);
-GO
-INSERT sys_role_menu VALUES (3, 1025);
-GO
-INSERT sys_role_menu VALUES (3, 1026);
-GO
-INSERT sys_role_menu VALUES (3, 1027);
-GO
-INSERT sys_role_menu VALUES (3, 1028);
-GO
-INSERT sys_role_menu VALUES (3, 1029);
-GO
-INSERT sys_role_menu VALUES (3, 1030);
-GO
-INSERT sys_role_menu VALUES (3, 1031);
-GO
-INSERT sys_role_menu VALUES (3, 1032);
-GO
-INSERT sys_role_menu VALUES (3, 1033);
-GO
-INSERT sys_role_menu VALUES (3, 1034);
-GO
-INSERT sys_role_menu VALUES (3, 1035);
-GO
-INSERT sys_role_menu VALUES (3, 1036);
-GO
-INSERT sys_role_menu VALUES (3, 1037);
-GO
-INSERT sys_role_menu VALUES (3, 1038);
-GO
-INSERT sys_role_menu VALUES (3, 1039);
-GO
-INSERT sys_role_menu VALUES (3, 1040);
-GO
-INSERT sys_role_menu VALUES (3, 1041);
-GO
-INSERT sys_role_menu VALUES (3, 1042);
-GO
-INSERT sys_role_menu VALUES (3, 1043);
-GO
-INSERT sys_role_menu VALUES (3, 1044);
-GO
-INSERT sys_role_menu VALUES (3, 1045);
-GO
-INSERT sys_role_menu VALUES (3, 1500);
-GO
-INSERT sys_role_menu VALUES (3, 1501);
-GO
-INSERT sys_role_menu VALUES (3, 1502);
-GO
-INSERT sys_role_menu VALUES (3, 1503);
-GO
-INSERT sys_role_menu VALUES (3, 1504);
-GO
-INSERT sys_role_menu VALUES (3, 1505);
-GO
-INSERT sys_role_menu VALUES (3, 1506);
-GO
-INSERT sys_role_menu VALUES (3, 1507);
-GO
-INSERT sys_role_menu VALUES (3, 1508);
-GO
-INSERT sys_role_menu VALUES (3, 1509);
-GO
-INSERT sys_role_menu VALUES (3, 1510);
-GO
-INSERT sys_role_menu VALUES (3, 1511);
-GO
-INSERT sys_role_menu VALUES (4, 5);
-GO
-INSERT sys_role_menu VALUES (4, 1500);
-GO
-INSERT sys_role_menu VALUES (4, 1501);
-GO
-INSERT sys_role_menu VALUES (4, 1502);
-GO
-INSERT sys_role_menu VALUES (4, 1503);
-GO
-INSERT sys_role_menu VALUES (4, 1504);
-GO
-INSERT sys_role_menu VALUES (4, 1505);
-GO
-INSERT sys_role_menu VALUES (4, 1506);
-GO
-INSERT sys_role_menu VALUES (4, 1507);
-GO
-INSERT sys_role_menu VALUES (4, 1508);
-GO
-INSERT sys_role_menu VALUES (4, 1509);
-GO
-INSERT sys_role_menu VALUES (4, 1510);
-GO
-INSERT sys_role_menu VALUES (4, 1511);
-GO
-
-INSERT sys_user_role VALUES (3, 3);
-GO
-INSERT sys_user_role VALUES (4, 4);
-GO
-
-INSERT test_demo VALUES (1, N'000000', 102, 4, 1, N'娴嬭瘯鏁版嵁鏉冮檺', N'娴嬭瘯', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (2, N'000000', 102, 3, 2, N'瀛愯妭鐐�1', N'111', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (3, N'000000', 102, 3, 3, N'瀛愯妭鐐�2', N'222', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (4, N'000000', 108, 4, 4, N'娴嬭瘯鏁版嵁', N'demo', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (5, N'000000', 108, 3, 13, N'瀛愯妭鐐�11', N'1111', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (6, N'000000', 108, 3, 12, N'瀛愯妭鐐�22', N'2222', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (7, N'000000', 108, 3, 11, N'瀛愯妭鐐�33', N'3333', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (8, N'000000', 108, 3, 10, N'瀛愯妭鐐�44', N'4444', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (9, N'000000', 108, 3, 9, N'瀛愯妭鐐�55', N'5555', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (10, N'000000', 108, 3, 8, N'瀛愯妭鐐�66', N'6666', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (11, N'000000', 108, 3, 7, N'瀛愯妭鐐�77', N'7777', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (12, N'000000', 108, 3, 6, N'瀛愯妭鐐�88', N'8888', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_demo VALUES (13, N'000000', 108, 3, 5, N'瀛愯妭鐐�99', N'9999', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-
-INSERT test_tree VALUES (1, N'000000', 0, 102, 4, N'娴嬭瘯鏁版嵁鏉冮檺', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (2, N'000000', 1, 102, 3, N'瀛愯妭鐐�1', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (3, N'000000', 2, 102, 3, N'瀛愯妭鐐�2', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (4, N'000000', 0, 108, 4, N'娴嬭瘯鏍�1', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (5, N'000000', 4, 108, 3, N'瀛愯妭鐐�11', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (6, N'000000', 4, 108, 3, N'瀛愯妭鐐�22', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (7, N'000000', 4, 108, 3, N'瀛愯妭鐐�33', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (8, N'000000', 5, 108, 3, N'瀛愯妭鐐�44', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (9, N'000000', 6, 108, 3, N'瀛愯妭鐐�55', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (10, N'000000', 7, 108, 3, N'瀛愯妭鐐�66', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (11, N'000000', 7, 108, 3, N'瀛愯妭鐐�77', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (12, N'000000', 10, 108, 3, N'瀛愯妭鐐�88', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
-INSERT test_tree VALUES (13, N'000000', 10, 108, 3, N'瀛愯妭鐐�99', 0, 103, getdate(), 1, NULL, NULL, 0);
-GO
diff --git a/script/sql/test.sql b/script/sql/test.sql
deleted file mode 100644
index d4cea05..0000000
--- a/script/sql/test.sql
+++ /dev/null
@@ -1,175 +0,0 @@
-DROP TABLE if EXISTS test_demo;
-CREATE TABLE test_demo
-(
- id bigint(0) NOT NULL COMMENT '涓婚敭',
- tenant_id varchar(20) NULL DEFAULT '000000' COMMENT '绉熸埛缂栧彿',
- dept_id bigint(0) NULL DEFAULT NULL COMMENT '閮ㄩ棬id',
- user_id bigint(0) NULL DEFAULT NULL COMMENT '鐢ㄦ埛id',
- order_num int(0) NULL DEFAULT 0 COMMENT '鎺掑簭鍙�',
- test_key varchar(255) NULL DEFAULT NULL COMMENT 'key閿�',
- value varchar(255) NULL DEFAULT NULL COMMENT '鍊�',
- version int(0) NULL DEFAULT 0 COMMENT '鐗堟湰',
- create_dept bigint(0) NULL DEFAULT NULL COMMENT '鍒涘缓閮ㄩ棬',
- create_time datetime(0) NULL DEFAULT NULL COMMENT '鍒涘缓鏃堕棿',
- create_by bigint(0) NULL DEFAULT NULL COMMENT '鍒涘缓浜�',
- update_time datetime(0) NULL DEFAULT NULL COMMENT '鏇存柊鏃堕棿',
- update_by bigint(0) NULL DEFAULT NULL COMMENT '鏇存柊浜�',
- del_flag int(0) NULL DEFAULT 0 COMMENT '鍒犻櫎鏍囧織',
- PRIMARY KEY (id) USING BTREE
-) ENGINE = InnoDB COMMENT = '娴嬭瘯鍗曡〃';
-
-DROP TABLE if EXISTS test_tree;
-CREATE TABLE test_tree
-(
- id bigint(0) NOT NULL COMMENT '涓婚敭',
- tenant_id varchar(20) NULL DEFAULT '000000' COMMENT '绉熸埛缂栧彿',
- parent_id bigint(0) NULL DEFAULT 0 COMMENT '鐖秈d',
- dept_id bigint(0) NULL DEFAULT NULL COMMENT '閮ㄩ棬id',
- user_id bigint(0) NULL DEFAULT NULL COMMENT '鐢ㄦ埛id',
- tree_name varchar(255) NULL DEFAULT NULL COMMENT '鍊�',
- version int(0) NULL DEFAULT 0 COMMENT '鐗堟湰',
- create_dept bigint(0) NULL DEFAULT NULL COMMENT '鍒涘缓閮ㄩ棬',
- create_time datetime(0) NULL DEFAULT NULL COMMENT '鍒涘缓鏃堕棿',
- create_by bigint(0) NULL DEFAULT NULL COMMENT '鍒涘缓浜�',
- update_time datetime(0) NULL DEFAULT NULL COMMENT '鏇存柊鏃堕棿',
- update_by bigint(0) NULL DEFAULT NULL COMMENT '鏇存柊浜�',
- del_flag int(0) NULL DEFAULT 0 COMMENT '鍒犻櫎鏍囧織',
- PRIMARY KEY (id) USING BTREE
-) ENGINE = InnoDB COMMENT = '娴嬭瘯鏍戣〃';
-
-INSERT INTO sys_user(user_id, tenant_id, dept_id, user_name, nick_name, user_type, email, phonenumber, sex, avatar, password, status, del_flag, login_ip, login_date, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (3, '000000', 108, 'test', '鏈儴闂ㄥ強浠ヤ笅 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', sysdate(), 103, 1, sysdate(), 3, sysdate(), NULL);
-INSERT INTO sys_user(user_id, tenant_id, dept_id, user_name, nick_name, user_type, email, phonenumber, sex, avatar, password, status, del_flag, login_ip, login_date, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (4, '000000', 102, 'test1', '浠呮湰浜� 瀵嗙爜666666', 'sys_user', '', '', '0', null, '$2a$10$b8yUzN0C71sbz.PhNOCgJe.Tu1yWC3RNrTyjSQ8p1W0.aaUXUJ.Ne', '0', '0', '127.0.0.1', sysdate(), 103, 1, sysdate(), 4, sysdate(), NULL);
-
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (5, '娴嬭瘯鑿滃崟', 0, 5, 'demo', NULL, 1, 0, 'M', '0', '0', NULL, 'star', 103, 1, sysdate(), NULL, NULL, '');
-
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1500, '娴嬭瘯鍗曡〃', 5, 1, 'demo', 'demo/demo/index', 1, 0, 'C', '0', '0', 'demo:demo:list', '#', 103, 1, sysdate(), NULL, NULL, '娴嬭瘯鍗曡〃鑿滃崟');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1501, '娴嬭瘯鍗曡〃鏌ヨ', 1500, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:query', '#', 103, 1, sysdate(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1502, '娴嬭瘯鍗曡〃鏂板', 1500, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:add', '#', 103, 1, sysdate(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1503, '娴嬭瘯鍗曡〃淇敼', 1500, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:edit', '#', 103, 1, sysdate(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1504, '娴嬭瘯鍗曡〃鍒犻櫎', 1500, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:remove', '#', 103, 1, sysdate(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1505, '娴嬭瘯鍗曡〃瀵煎嚭', 1500, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:demo:export', '#', 103, 1, sysdate(), NULL, NULL, '');
-
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1506, '娴嬭瘯鏍戣〃', 5, 1, 'tree', 'demo/tree/index', 1, 0, 'C', '0', '0', 'demo:tree:list', '#', 103, 1, sysdate(), NULL, NULL, '娴嬭瘯鏍戣〃鑿滃崟');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1507, '娴嬭瘯鏍戣〃鏌ヨ', 1506, 1, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:query', '#', 103, 1, sysdate(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1508, '娴嬭瘯鏍戣〃鏂板', 1506, 2, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:add', '#', 103, 1, sysdate(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1509, '娴嬭瘯鏍戣〃淇敼', 1506, 3, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:edit', '#', 103, 1, sysdate(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1510, '娴嬭瘯鏍戣〃鍒犻櫎', 1506, 4, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:remove', '#', 103, 1, sysdate(), NULL, NULL, '');
-INSERT INTO sys_menu(menu_id, menu_name, parent_id, order_num, path, component, is_frame, is_cache, menu_type, visible, status, perms, icon, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (1511, '娴嬭瘯鏍戣〃瀵煎嚭', 1506, 5, '#', '', 1, 0, 'F', '0', '0', 'demo:tree:export', '#', 103, 1, sysdate(), NULL, NULL, '');
-
-INSERT INTO sys_role(role_id, tenant_id, role_name, role_key, role_sort, data_scope, menu_check_strictly, dept_check_strictly, status, del_flag, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (3, '000000', '鏈儴闂ㄥ強浠ヤ笅', 'test1', 3, '4', 1, 1, '0', '0', 103, 1, sysdate(), 1, NULL, NULL);
-INSERT INTO sys_role(role_id, tenant_id, role_name, role_key, role_sort, data_scope, menu_check_strictly, dept_check_strictly, status, del_flag, create_dept, create_by, create_time, update_by, update_time, remark) VALUES (4, '000000', '浠呮湰浜�', 'test2', 4, '5', 1, 1, '0', '0', 103, 1, sysdate(), 1, NULL, NULL);
-
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 5);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 100);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 101);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 102);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 103);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 104);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 105);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 106);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 107);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 108);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 500);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 501);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1001);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1002);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1003);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1004);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1005);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1006);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1007);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1008);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1009);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1010);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1011);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1012);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1013);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1014);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1015);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1016);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1017);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1018);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1019);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1020);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1021);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1022);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1023);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1024);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1025);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1026);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1027);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1028);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1029);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1030);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1031);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1032);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1033);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1034);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1035);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1036);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1037);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1038);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1039);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1040);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1041);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1042);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1043);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1044);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1045);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1500);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1501);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1502);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1503);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1504);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1505);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1506);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1507);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1508);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1509);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1510);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (3, 1511);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 5);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1500);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1501);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1502);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1503);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1504);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1505);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1506);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1507);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1508);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1509);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1510);
-INSERT INTO sys_role_menu(role_id, menu_id) VALUES (4, 1511);
-
-INSERT INTO sys_user_role(user_id, role_id) VALUES (3, 3);
-INSERT INTO sys_user_role(user_id, role_id) VALUES (4, 4);
-
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (1, '000000', 102, 4, 1, '娴嬭瘯鏁版嵁鏉冮檺', '娴嬭瘯', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (2, '000000', 102, 3, 2, '瀛愯妭鐐�1', '111', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (3, '000000', 102, 3, 3, '瀛愯妭鐐�2', '222', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (4, '000000', 108, 4, 4, '娴嬭瘯鏁版嵁', 'demo', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (5, '000000', 108, 3, 13, '瀛愯妭鐐�11', '1111', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (6, '000000', 108, 3, 12, '瀛愯妭鐐�22', '2222', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (7, '000000', 108, 3, 11, '瀛愯妭鐐�33', '3333', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (8, '000000', 108, 3, 10, '瀛愯妭鐐�44', '4444', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (9, '000000', 108, 3, 9, '瀛愯妭鐐�55', '5555', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (10, '000000', 108, 3, 8, '瀛愯妭鐐�66', '6666', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (11, '000000', 108, 3, 7, '瀛愯妭鐐�77', '7777', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (12, '000000', 108, 3, 6, '瀛愯妭鐐�88', '8888', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_demo(id, tenant_id, dept_id, user_id, order_num, test_key, value, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (13, '000000', 108, 3, 5, '瀛愯妭鐐�99', '9999', 0, 103, sysdate(), 1, NULL, NULL, 0);
-
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (1, '000000', 0, 102, 4, '娴嬭瘯鏁版嵁鏉冮檺', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (2, '000000', 1, 102, 3, '瀛愯妭鐐�1', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (3, '000000', 2, 102, 3, '瀛愯妭鐐�2', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (4, '000000', 0, 108, 4, '娴嬭瘯鏍�1', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (5, '000000', 4, 108, 3, '瀛愯妭鐐�11', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (6, '000000', 4, 108, 3, '瀛愯妭鐐�22', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (7, '000000', 4, 108, 3, '瀛愯妭鐐�33', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (8, '000000', 5, 108, 3, '瀛愯妭鐐�44', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (9, '000000', 6, 108, 3, '瀛愯妭鐐�55', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (10, '000000', 7, 108, 3, '瀛愯妭鐐�66', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (11, '000000', 7, 108, 3, '瀛愯妭鐐�77', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (12, '000000', 10, 108, 3, '瀛愯妭鐐�88', 0, 103, sysdate(), 1, NULL, NULL, 0);
-INSERT INTO test_tree(id, tenant_id, parent_id, dept_id, user_id, tree_name, version, create_dept, create_time, create_by, update_time, update_by, del_flag) VALUES (13, '000000', 10, 108, 3, '瀛愯妭鐐�99', 0, 103, sysdate(), 1, NULL, NULL, 0);
diff --git a/script/sql/update/oracle/update_5.0-5.1.sql b/script/sql/update/oracle/update_5.0-5.1.sql
index 363d4ab..09cfae8 100644
--- a/script/sql/update/oracle/update_5.0-5.1.sql
+++ b/script/sql/update/oracle/update_5.0-5.1.sql
@@ -98,7 +98,7 @@
alter table sys_client add constraint pk_sys_client primary key (id);
comment on table sys_client is '绯荤粺鎺堟潈琛�';
-comment on column sys_client.id is '涓诲缓';
+comment on column sys_client.id is '涓婚敭';
comment on column sys_client.client_id is '瀹㈡埛绔痠d';
comment on column sys_client.client_key is '瀹㈡埛绔痥ey';
comment on column sys_client.client_secret is '瀹㈡埛绔閽�';
diff --git a/script/sql/update/oracle/update_5.1.0-5.1.1.sql b/script/sql/update/oracle/update_5.1.0-5.1.1.sql
index 5382583..979a4bd 100644
--- a/script/sql/update/oracle/update_5.1.0-5.1.1.sql
+++ b/script/sql/update/oracle/update_5.1.0-5.1.1.sql
@@ -1,5 +1,5 @@
-ALTER TABLE sys_logininfor ADD (client_key VARCHAR(32) DEFAULT '');
+ALTER TABLE sys_logininfor ADD (client_key varchar2(32) DEFAULT '');
COMMENT ON COLUMN sys_logininfor.client_key IS '瀹㈡埛绔�';
-ALTER TABLE sys_logininfor ADD (device_type VARCHAR(32) DEFAULT '');
+ALTER TABLE sys_logininfor ADD (device_type varchar2(32) DEFAULT '');
COMMENT ON COLUMN sys_logininfor.device_type IS '璁惧绫诲瀷';
diff --git a/script/sql/update/oracle/update_5.1.1-5.1.2.sql b/script/sql/update/oracle/update_5.1.1-5.1.2.sql
index dcb5cbb..d7c030c 100644
--- a/script/sql/update/oracle/update_5.1.1-5.1.2.sql
+++ b/script/sql/update/oracle/update_5.1.1-5.1.2.sql
@@ -3,3 +3,4 @@
insert into sys_menu values('1621', '閰嶇疆娣诲姞', '118', '6', '#', '', '', 1, 0, 'F', '0', '0', 'system:ossConfig:add', '#', 103, 1, sysdate, null, null, '');
insert into sys_menu values('1622', '閰嶇疆缂栬緫', '118', '6', '#', '', '', 1, 0, 'F', '0', '0', 'system:ossConfig:edit', '#', 103, 1, sysdate, null, null, '');
insert into sys_menu values('1623', '閰嶇疆鍒犻櫎', '118', '6', '#', '', '', 1, 0, 'F', '0', '0', 'system:ossConfig:remove', '#', 103, 1, sysdate, null, null, '');
+
diff --git a/script/sql/update/oracle/update_5.1.2-5.2.0.sql b/script/sql/update/oracle/update_5.1.2-5.2.0.sql
new file mode 100644
index 0000000..0f87fd6
--- /dev/null
+++ b/script/sql/update/oracle/update_5.1.2-5.2.0.sql
@@ -0,0 +1,9 @@
+ALTER TABLE sys_dept ADD (dept_category varchar2(100) DEFAULT NULL) COMMENT '閮ㄩ棬绫诲埆缂栫爜';
+COMMENT ON COLUMN sys_dept.dept_category IS '閮ㄩ棬绫诲埆缂栫爜';
+ALTER TABLE sys_post ADD (dept_id number(20) NOT NULL) COMMENT '閮ㄩ棬id';
+COMMENT ON COLUMN sys_post.dept_id IS '閮ㄩ棬id';
+ALTER TABLE sys_post ADD (post_category VARCHAR2(100) DEFAULT NULL) COMMENT '宀椾綅绫诲埆缂栫爜';
+COMMENT ON COLUMN sys_post.post_category IS '宀椾綅绫诲埆缂栫爜';
+UPDATE sys_post SET dept_id = 100;
+UPDATE sys_post SET dept_id = 103 where post_id = 1;
+UPDATE sys_menu SET path = 'snailjob', component = 'monitor/snailjob/index', perms = 'monitor:snailjob:list', remark = 'SnailJob鎺у埗鍙拌彍鍗�' WHERE menu_id = 120;
diff --git a/script/sql/update/postgres/update_5.0-5.1.sql b/script/sql/update/postgres/update_5.0-5.1.sql
index fa2eb3e..f5f0a5c 100644
--- a/script/sql/update/postgres/update_5.0-5.1.sql
+++ b/script/sql/update/postgres/update_5.0-5.1.sql
@@ -97,7 +97,7 @@
);
comment on table sys_client is '绯荤粺鎺堟潈琛�';
-comment on column sys_client.id is '涓诲缓';
+comment on column sys_client.id is '涓婚敭';
comment on column sys_client.client_id is '瀹㈡埛绔痠d';
comment on column sys_client.client_key is '瀹㈡埛绔痥ey';
comment on column sys_client.client_secret is '瀹㈡埛绔閽�';
diff --git a/script/sql/update/postgres/update_5.1.1-5.1.2.sql b/script/sql/update/postgres/update_5.1.1-5.1.2.sql
index 0e212de..62eb836 100644
--- a/script/sql/update/postgres/update_5.1.1-5.1.2.sql
+++ b/script/sql/update/postgres/update_5.1.1-5.1.2.sql
@@ -3,4 +3,3 @@
insert into sys_menu values('1621', '閰嶇疆娣诲姞', '118', '6', '#', '', '', '1', '0', 'F', '0', '0', 'system:ossConfig:add', '#', 103, 1, now(), null, null, '');
insert into sys_menu values('1622', '閰嶇疆缂栬緫', '118', '6', '#', '', '', '1', '0', 'F', '0', '0', 'system:ossConfig:edit', '#', 103, 1, now(), null, null, '');
insert into sys_menu values('1623', '閰嶇疆鍒犻櫎', '118', '6', '#', '', '', '1', '0', 'F', '0', '0', 'system:ossConfig:remove', '#', 103, 1, now(), null, null, '');
-
diff --git a/script/sql/update/postgres/update_5.1.2-5.2.0.sql b/script/sql/update/postgres/update_5.1.2-5.2.0.sql
new file mode 100644
index 0000000..dc36ebf
--- /dev/null
+++ b/script/sql/update/postgres/update_5.1.2-5.2.0.sql
@@ -0,0 +1,9 @@
+ALTER TABLE sys_dept ADD COLUMN dept_category varchar(100) default null::varchar;
+COMMENT ON COLUMN sys_dept.dept_category IS '瀹㈡埛绔�';
+ALTER TABLE sys_post ADD COLUMN dept_id int8 NOT NULL;
+COMMENT ON COLUMN sys_post.dept_id IS '閮ㄩ棬id';
+ALTER TABLE sys_post ADD COLUMN post_category varchar(100) default null::varchar;
+COMMENT ON COLUMN sys_post.post_category IS '宀椾綅绫诲埆缂栫爜';
+UPDATE sys_post SET dept_id = 100;
+UPDATE sys_post SET dept_id = 103 where post_id = 1;
+UPDATE sys_menu SET path = 'snailjob', component = 'monitor/snailjob/index', perms = 'monitor:snailjob:list', remark = 'SnailJob鎺у埗鍙拌彍鍗�' WHERE menu_id = 120;
diff --git a/script/sql/update/sqlserver/update_5.0-5.1.sql b/script/sql/update/sqlserver/update_5.0-5.1.sql
index 605f02f..bde3813 100644
--- a/script/sql/update/sqlserver/update_5.0-5.1.sql
+++ b/script/sql/update/sqlserver/update_5.0-5.1.sql
@@ -250,7 +250,7 @@
GO
EXEC sp_addextendedproperty
-'MS_Description', N'涓诲缓',
+'MS_Description', N'涓婚敭',
'SCHEMA', N'dbo',
'TABLE', N'sys_client',
'COLUMN', N'id'
diff --git a/script/sql/update/sqlserver/update_5.1.2-5.2.0.sql b/script/sql/update/sqlserver/update_5.1.2-5.2.0.sql
new file mode 100644
index 0000000..bf69f10
--- /dev/null
+++ b/script/sql/update/sqlserver/update_5.1.2-5.2.0.sql
@@ -0,0 +1,29 @@
+ALTER TABLE sys_dept ADD dept_category nvarchar(100) DEFAULT NULL
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閮ㄩ棬绫诲埆缂栫爜',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_dept',
+ 'COLUMN', N'dept_category'
+GO
+ALTER TABLE sys_post ADD dept_id bigint NOT NULL
+GO
+ALTER TABLE sys_post ADD post_category nvarchar(100) DEFAULT NULL
+GO
+EXEC sp_addextendedproperty
+ 'MS_Description', N'閮ㄩ棬id',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_post',
+ 'COLUMN', N'dept_id'
+GO
+EXEC sp_addextendedproperty
+ 'MS_Description', N'宀椾綅绫诲埆缂栫爜',
+ 'SCHEMA', N'dbo',
+ 'TABLE', N'sys_post',
+ 'COLUMN', N'post_category'
+GO
+UPDATE sys_post SET dept_id = 100
+GO
+UPDATE sys_post SET dept_id = 103 where post_id = 1
+GO
+UPDATE sys_menu SET path = N'snailjob', component = N'monitor/snailjob/index', perms = N'monitor:snailjob:list', remark = N'SnailJob鎺у埗鍙拌彍鍗�' WHERE menu_id = 120
+GO
\ No newline at end of file
diff --git a/script/sql/update/update_5.1.1-5.1.2.sql b/script/sql/update/update_5.1.1-5.1.2.sql
index 6813949..314743f 100644
--- a/script/sql/update/update_5.1.1-5.1.2.sql
+++ b/script/sql/update/update_5.1.1-5.1.2.sql
@@ -3,4 +3,3 @@
insert into sys_menu values('1621', '閰嶇疆娣诲姞', '118', '6', '#', '', '', 1, 0, 'F', '0', '0', 'system:ossConfig:add', '#', 103, 1, sysdate(), null, null, '');
insert into sys_menu values('1622', '閰嶇疆缂栬緫', '118', '6', '#', '', '', 1, 0, 'F', '0', '0', 'system:ossConfig:edit', '#', 103, 1, sysdate(), null, null, '');
insert into sys_menu values('1623', '閰嶇疆鍒犻櫎', '118', '6', '#', '', '', 1, 0, 'F', '0', '0', 'system:ossConfig:remove', '#', 103, 1, sysdate(), null, null, '');
-
diff --git a/script/sql/update/update_5.1.2-5.2.0.sql b/script/sql/update/update_5.1.2-5.2.0.sql
new file mode 100644
index 0000000..11d71c8
--- /dev/null
+++ b/script/sql/update/update_5.1.2-5.2.0.sql
@@ -0,0 +1,5 @@
+ALTER TABLE sys_dept ADD dept_category VARCHAR(100) DEFAULT NULL COMMENT '閮ㄩ棬绫诲埆缂栫爜';
+ALTER TABLE sys_post ADD dept_id BIGINT(20) NOT NULL COMMENT '閮ㄩ棬id', ADD post_category VARCHAR(100) DEFAULT NULL COMMENT '宀椾綅绫诲埆缂栫爜';
+UPDATE sys_post SET dept_id = 100;
+UPDATE sys_post SET dept_id = 103 where post_id = 1;
+UPDATE sys_menu SET path = 'snailjob', component = 'monitor/snailjob/index', perms = 'monitor:snailjob:list', remark = 'SnailJob鎺у埗鍙拌彍鍗�' WHERE menu_id = 120;
--
Gitblit v1.9.3