Procházet zdrojové kódy

Merge remote-tracking branch 'upstream/master'

“zyj” před 4 roky
rodič
revize
82bff6ddb5

+ 1 - 0
README.md

@@ -17,6 +17,7 @@
 * 权限认证使用Jwt,支持多终端认证系统。
 * 支持加载动态权限菜单,多方式轻松权限控制。
 * 高效率开发,使用代码生成器可以一键生成前后端代码。
+* 提供了技术栈([Vue3](https://v3.cn.vuejs.org) [Element Plus](https://element-plus.org/zh-CN) [Vite](https://cn.vitejs.dev))版本[RuoYi-Vue3](https://github.com/yangzongzhuan/RuoYi-Vue3),保持同步更新。
 * 提供了单应用版本[RuoYi-Vue-fast](https://github.com/yangzongzhuan/RuoYi-Vue-fast),Oracle版本[RuoYi-Vue-Oracle](https://github.com/yangzongzhuan/RuoYi-Vue-Oracle),保持同步更新。
 * 不分离版本,请移步[RuoYi](https://gitee.com/y_project/RuoYi),微服务版本,请移步[RuoYi-Cloud](https://gitee.com/y_project/RuoYi-Cloud)
 * 特别鸣谢:[element](https://github.com/ElemeFE/element),[vue-element-admin](https://github.com/PanJiaChen/vue-element-admin),[eladmin-web](https://github.com/elunez/eladmin-web)。

+ 2 - 2
pom.xml

@@ -6,14 +6,14 @@
 	
     <groupId>com.ruoyi</groupId>
     <artifactId>ruoyi</artifactId>
-    <version>3.7.0</version>
+    <version>3.8.0</version>
 
     <name>ruoyi</name>
     <url>http://www.ruoyi.vip</url>
     <description>若依管理系统</description>
     
     <properties>
-        <ruoyi.version>3.7.0</ruoyi.version>
+        <ruoyi.version>3.8.0</ruoyi.version>
         <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
         <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
         <java.version>1.8</java.version>

+ 1 - 1
ruoyi-admin/pom.xml

@@ -5,7 +5,7 @@
     <parent>
         <artifactId>ruoyi</artifactId>
         <groupId>com.ruoyi</groupId>
-        <version>3.7.0</version>
+        <version>3.8.0</version>
     </parent>
     <modelVersion>4.0.0</modelVersion>
     <packaging>jar</packaging>

+ 1 - 1
ruoyi-admin/src/main/java/com/ruoyi/web/controller/system/SysProfileController.java

@@ -72,7 +72,7 @@ public class SysProfileController extends BaseController
                 && UserConstants.NOT_UNIQUE.equals(userService.checkEmailUnique(user)))
         {
             return AjaxResult.error("修改用户'" + user.getUserName() + "'失败,邮箱账号已存在");
-        }       
+        }
         user.setUserId(sysUser.getUserId());
         user.setPassword(null);
         if (userService.updateUserProfile(user) > 0)

+ 8 - 5
ruoyi-admin/src/main/resources/application.yml

@@ -3,7 +3,7 @@ ruoyi:
   # 名称
   name: RuoYi
   # 版本
-  version: 3.7.0
+  version: 3.8.0
   # 版权年份
   copyrightYear: 2021
   # 实例演示开关
@@ -25,10 +25,13 @@ server:
   tomcat:
     # tomcat的URI编码
     uri-encoding: UTF-8
-    # tomcat最大线程数,默认为200
-    max-threads: 800
-    # Tomcat启动初始化的线程数,默认值25
-    min-spare-threads: 30
+    # 连接数满后的排队数,默认为100
+    accept-count: 1000
+    threads:
+      # tomcat最大线程数,默认为200
+      max: 800
+      # Tomcat启动初始化的线程数,默认值10
+      min-spare: 100
 
 # 日志配置
 logging:

+ 1 - 1
ruoyi-common/pom.xml

@@ -5,7 +5,7 @@
     <parent>
         <artifactId>ruoyi</artifactId>
         <groupId>com.ruoyi</groupId>
-        <version>3.7.0</version>
+        <version>3.8.0</version>
     </parent>
     <modelVersion>4.0.0</modelVersion>
 

+ 1 - 1
ruoyi-framework/pom.xml

@@ -5,7 +5,7 @@
     <parent>
         <artifactId>ruoyi</artifactId>
         <groupId>com.ruoyi</groupId>
-        <version>3.7.0</version>
+        <version>3.8.0</version>
     </parent>
     <modelVersion>4.0.0</modelVersion>
 

+ 1 - 1
ruoyi-generator/pom.xml

@@ -5,7 +5,7 @@
     <parent>
         <artifactId>ruoyi</artifactId>
         <groupId>com.ruoyi</groupId>
-        <version>3.7.0</version>
+        <version>3.8.0</version>
     </parent>
     <modelVersion>4.0.0</modelVersion>
 

+ 1 - 1
ruoyi-quartz/pom.xml

@@ -5,7 +5,7 @@
     <parent>
         <artifactId>ruoyi</artifactId>
         <groupId>com.ruoyi</groupId>
-        <version>3.7.0</version>
+        <version>3.8.0</version>
     </parent>
     <modelVersion>4.0.0</modelVersion>
 

+ 1 - 1
ruoyi-system/pom.xml

@@ -5,7 +5,7 @@
     <parent>
         <artifactId>ruoyi</artifactId>
         <groupId>com.ruoyi</groupId>
-        <version>3.7.0</version>
+        <version>3.8.0</version>
     </parent>
     <modelVersion>4.0.0</modelVersion>
 

+ 13 - 2
ruoyi-system/src/main/java/com/ruoyi/system/service/impl/SysMenuServiceImpl.java

@@ -179,7 +179,7 @@ public class SysMenuServiceImpl implements ISysMenuService
                 router.setPath("/inner");
                 List<RouterVo> childrenList = new ArrayList<RouterVo>();
                 RouterVo children = new RouterVo();
-                String routerPath = StringUtils.replaceEach(menu.getPath(), new String[] { Constants.HTTP, Constants.HTTPS }, new String[] { "", "" });
+                String routerPath = innerLinkReplaceEach(menu.getPath());
                 children.setPath(routerPath);
                 children.setComponent(UserConstants.INNER_LINK);
                 children.setName(StringUtils.capitalize(routerPath));
@@ -358,7 +358,7 @@ public class SysMenuServiceImpl implements ISysMenuService
         // 内链打开外网方式
         if (menu.getParentId().intValue() != 0 && isInnerLink(menu))
         {
-            routerPath = StringUtils.replaceEach(routerPath, new String[] { Constants.HTTP, Constants.HTTPS }, new String[] { "", "" });
+            routerPath = innerLinkReplaceEach(routerPath);
         }
         // 非外链并且是一级目录(类型为目录)
         if (0 == menu.getParentId().intValue() && UserConstants.TYPE_DIR.equals(menu.getMenuType())
@@ -500,4 +500,15 @@ public class SysMenuServiceImpl implements ISysMenuService
     {
         return getChildList(list, t).size() > 0 ? true : false;
     }
+
+    /**
+     * 内链域名特殊字符替换
+     * 
+     * @return
+     */
+    public String innerLinkReplaceEach(String path)
+    {
+        return StringUtils.replaceEach(path, new String[] { Constants.HTTP, Constants.HTTPS },
+                new String[] { "", "" });
+    }
 }

+ 1 - 1
ruoyi-ui/package.json

@@ -1,6 +1,6 @@
 {
   "name": "ruoyi",
-  "version": "3.7.0",
+  "version": "3.8.0",
   "description": "若依管理系统",
   "author": "若依",
   "license": "MIT",

+ 24 - 42
ruoyi-ui/src/components/Crontab/day.vue

@@ -2,7 +2,7 @@
 	<el-form size="small">
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="1">
-				日,允许的通配符[, - * / L M]
+				日,允许的通配符[, - * ? / L W]
 			</el-radio>
 		</el-form-item>
 
@@ -15,23 +15,23 @@
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="3">
 				周期从
-				<el-input-number v-model='cycle01' :min="0" :max="31" /> -
-				<el-input-number v-model='cycle02' :min="0" :max="31" /> 日
+				<el-input-number v-model='cycle01' :min="1" :max="30" /> -
+				<el-input-number v-model='cycle02' :min="cycle01 ? cycle01 + 1 : 2" :max="31" /> 日
 			</el-radio>
 		</el-form-item>
 
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="4">
-				<el-input-number v-model='average01' :min="0" :max="31" /> 号开始,每
-				<el-input-number v-model='average02' :min="0" :max="31" /> 日执行一次
+				<el-input-number v-model='average01' :min="1" :max="30" /> 号开始,每
+				<el-input-number v-model='average02' :min="1" :max="31 - average01 || 1" /> 日执行一次
 			</el-radio>
 		</el-form-item>
 
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="5">
 				每月
-				<el-input-number v-model='workday' :min="0" :max="31" /> 号最近的那个工作日
+				<el-input-number v-model='workday' :min="1" :max="31" /> 号最近的那个工作日
 			</el-radio>
 		</el-form-item>
 
@@ -72,31 +72,22 @@ export default {
 		// 单选按钮值变化时
 		radioChange() {
 			('day rachange');
-			if (this.radioValue === 1) {
-				this.$emit('update', 'day', '*', 'day');
-				this.$emit('update', 'week', '?', 'day');
-				this.$emit('update', 'month', '*', 'day');
-			} else {
-				if (this.cron.hour === '*') {
-					this.$emit('update', 'hour', '0', 'day');
-				}
-				if (this.cron.min === '*') {
-					this.$emit('update', 'min', '0', 'day');
-				}
-				if (this.cron.second === '*') {
-					this.$emit('update', 'second', '0', 'day');
-				}
+			if (this.radioValue !== 2 && this.cron.week !== '?') {
+				this.$emit('update', 'week', '?', 'day')
 			}
 
 			switch (this.radioValue) {
+				case 1:
+					this.$emit('update', 'day', '*');
+					break;
 				case 2:
 					this.$emit('update', 'day', '?');
 					break;
 				case 3:
-					this.$emit('update', 'day', this.cycle01 + '-' + this.cycle02);
+					this.$emit('update', 'day', this.cycleTotal);
 					break;
 				case 4:
-					this.$emit('update', 'day', this.average01 + '/' + this.average02);
+					this.$emit('update', 'day', this.averageTotal);
 					break;
 				case 5:
 					this.$emit('update', 'day', this.workday + 'W');
@@ -125,7 +116,7 @@ export default {
 		// 最近工作日值变化时
 		workdayChange() {
 			if (this.radioValue == '5') {
-				this.$emit('update', 'day', this.workday + 'W');
+				this.$emit('update', 'day', this.workdayCheck + 'W');
 			}
 		},
 		// checkbox值变化时
@@ -133,19 +124,10 @@ export default {
 			if (this.radioValue == '7') {
 				this.$emit('update', 'day', this.checkboxString);
 			}
-		},
-		// 父组件传递的week发生变化触发
-		weekChange() {
-			//判断week值与day不能同时为“?”
-			if (this.cron.week == '?' && this.radioValue == '2') {
-				this.radioValue = '1';
-			} else if (this.cron.week !== '?' && this.radioValue != '2') {
-				this.radioValue = '2';
-			}
-		},
+		}
 	},
 	watch: {
-		"radioValue": "radioChange",
+		'radioValue': 'radioChange',
 		'cycleTotal': 'cycleChange',
 		'averageTotal': 'averageChange',
 		'workdayCheck': 'workdayChange',
@@ -154,20 +136,20 @@ export default {
 	computed: {
 		// 计算两个周期值
 		cycleTotal: function () {
-			this.cycle01 = this.checkNum(this.cycle01, 1, 31)
-			this.cycle02 = this.checkNum(this.cycle02, 1, 31)
-			return this.cycle01 + '-' + this.cycle02;
+			const cycle01 = this.checkNum(this.cycle01, 1, 30)
+			const cycle02 = this.checkNum(this.cycle02, cycle01 ? cycle01 + 1 : 2, 31, 31)
+			return cycle01 + '-' + cycle02;
 		},
 		// 计算平均用到的值
 		averageTotal: function () {
-			this.average01 = this.checkNum(this.average01, 1, 31)
-			this.average02 = this.checkNum(this.average02, 1, 31)
-			return this.average01 + '/' + this.average02;
+			const average01 = this.checkNum(this.average01, 1, 30)
+			const average02 = this.checkNum(this.average02, 1, 31 - average01 || 0)
+			return average01 + '/' + average02;
 		},
 		// 计算工作日格式
 		workdayCheck: function () {
-			this.workday = this.checkNum(this.workday, 1, 31)
-			return this.workday;
+			const workday = this.checkNum(this.workday, 1, 31)
+			return workday;
 		},
 		// 计算勾选的checkbox值合集
 		checkboxString: function () {

+ 16 - 24
ruoyi-ui/src/components/Crontab/hour.vue

@@ -9,16 +9,16 @@
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="2">
 				周期从
-				<el-input-number v-model='cycle01' :min="0" :max="60" /> -
-				<el-input-number v-model='cycle02' :min="0" :max="60" /> 小时
+				<el-input-number v-model='cycle01' :min="0" :max="22" /> -
+				<el-input-number v-model='cycle02' :min="cycle01 ? cycle01 + 1 : 1" :max="23" /> 小时
 			</el-radio>
 		</el-form-item>
 
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="3">
-				<el-input-number v-model='average01' :min="0" :max="60" /> 小时开始,每
-				<el-input-number v-model='average02' :min="0" :max="60" /> 小时执行一次
+				<el-input-number v-model='average01' :min="0" :max="22" /> 小时开始,每
+				<el-input-number v-model='average02' :min="1" :max="23 - average01 || 0" /> 小时执行一次
 			</el-radio>
 		</el-form-item>
 
@@ -51,23 +51,15 @@ export default {
 	methods: {
 		// 单选按钮值变化时
 		radioChange() {
-			if (this.radioValue === 1) {
-				this.$emit('update', 'hour', '*', 'hour');
-				this.$emit('update', 'day', '*', 'hour');
-			} else {
-				if (this.cron.min === '*') {
-					this.$emit('update', 'min', '0', 'hour');
-				}
-				if (this.cron.second === '*') {
-					this.$emit('update', 'second', '0', 'hour');
-				}
-			}
 			switch (this.radioValue) {
+				case 1:
+        	this.$emit('update', 'hour', '*')
+        	break;
 				case 2:
-					this.$emit('update', 'hour', this.cycle01 + '-' + this.cycle02);
+					this.$emit('update', 'hour', this.cycleTotal);
 					break;
 				case 3:
-					this.$emit('update', 'hour', this.average01 + '/' + this.average02);
+					this.$emit('update', 'hour', this.averageTotal);
 					break;
 				case 4:
 					this.$emit('update', 'hour', this.checkboxString);
@@ -94,7 +86,7 @@ export default {
 		}
 	},
 	watch: {
-		"radioValue": "radioChange",
+		'radioValue': 'radioChange',
 		'cycleTotal': 'cycleChange',
 		'averageTotal': 'averageChange',
 		'checkboxString': 'checkboxChange'
@@ -102,15 +94,15 @@ export default {
 	computed: {
 		// 计算两个周期值
 		cycleTotal: function () {
-			this.cycle01 = this.checkNum(this.cycle01, 0, 23)
-			this.cycle02 = this.checkNum(this.cycle02, 0, 23)
-			return this.cycle01 + '-' + this.cycle02;
+			const cycle01 = this.checkNum(this.cycle01, 0, 22)
+			const cycle02 = this.checkNum(this.cycle02, cycle01 ? cycle01 + 1 : 1, 23)
+			return cycle01 + '-' + cycle02;
 		},
 		// 计算平均用到的值
 		averageTotal: function () {
-			this.average01 = this.checkNum(this.average01, 0, 23)
-			this.average02 = this.checkNum(this.average02, 1, 23)
-			return this.average01 + '/' + this.average02;
+			const average01 = this.checkNum(this.average01, 0, 22)
+			const average02 = this.checkNum(this.average02, 1, 23 - average01 || 0)
+			return average01 + '/' + average02;
 		},
 		// 计算勾选的checkbox值合集
 		checkboxString: function () {

+ 6 - 1
ruoyi-ui/src/components/Crontab/index.vue

@@ -2,7 +2,12 @@
   <div>
     <el-tabs type="border-card">
       <el-tab-pane label="秒" v-if="shouldHide('second')">
-        <CrontabSecond @update="updateCrontabValue" :check="checkNumber" ref="cronsecond" />
+        <CrontabSecond
+          @update="updateCrontabValue"
+          :check="checkNumber"
+          :cron="crontabValueObj"
+          ref="cronsecond"
+        />
       </el-tab-pane>
 
       <el-tab-pane label="分钟" v-if="shouldHide('min')">

+ 13 - 17
ruoyi-ui/src/components/Crontab/min.vue

@@ -9,16 +9,16 @@
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="2">
 				周期从
-				<el-input-number v-model='cycle01' :min="0" :max="60" /> -
-				<el-input-number v-model='cycle02' :min="0" :max="60" /> 分钟
+				<el-input-number v-model='cycle01' :min="0" :max="58" /> -
+				<el-input-number v-model='cycle02' :min="cycle01 ? cycle01 + 1 : 1" :max="59" /> 分钟
 			</el-radio>
 		</el-form-item>
 
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="3">
-				<el-input-number v-model='average01' :min="0" :max="60" /> 分钟开始,每
-				<el-input-number v-model='average02' :min="0" :max="60" /> 分钟执行一次
+				<el-input-number v-model='average01' :min="0" :max="58" /> 分钟开始,每
+				<el-input-number v-model='average02' :min="1" :max="59 - average01 || 0" /> 分钟执行一次
 			</el-radio>
 		</el-form-item>
 
@@ -52,19 +52,15 @@ export default {
 	methods: {
 		// 单选按钮值变化时
 		radioChange() {
-			if (this.radioValue !== 1 && this.cron.second === '*') {
-				this.$emit('update', 'second', '0', 'min');
-			}
 			switch (this.radioValue) {
 				case 1:
 					this.$emit('update', 'min', '*', 'min');
-					this.$emit('update', 'hour', '*', 'min');
 					break;
 				case 2:
-					this.$emit('update', 'min', this.cycle01 + '-' + this.cycle02, 'min');
+					this.$emit('update', 'min', this.cycleTotal, 'min');
 					break;
 				case 3:
-					this.$emit('update', 'min', this.average01 + '/' + this.average02, 'min');
+					this.$emit('update', 'min', this.averageTotal, 'min');
 					break;
 				case 4:
 					this.$emit('update', 'min', this.checkboxString, 'min');
@@ -92,7 +88,7 @@ export default {
 
 	},
 	watch: {
-		"radioValue": "radioChange",
+		'radioValue': 'radioChange',
 		'cycleTotal': 'cycleChange',
 		'averageTotal': 'averageChange',
 		'checkboxString': 'checkboxChange',
@@ -100,15 +96,15 @@ export default {
 	computed: {
 		// 计算两个周期值
 		cycleTotal: function () {
-			this.cycle01 = this.checkNum(this.cycle01, 0, 59)
-			this.cycle02 = this.checkNum(this.cycle02, 0, 59)
-			return this.cycle01 + '-' + this.cycle02;
+			const cycle01 = this.checkNum(this.cycle01, 0, 58)
+			const cycle02 = this.checkNum(this.cycle02, cycle01 ? cycle01 + 1 : 1, 59)
+			return cycle01 + '-' + cycle02;
 		},
 		// 计算平均用到的值
 		averageTotal: function () {
-			this.average01 = this.checkNum(this.average01, 0, 59)
-			this.average02 = this.checkNum(this.average02, 1, 59)
-			return this.average01 + '/' + this.average02;
+			const average01 = this.checkNum(this.average01, 0, 58)
+			const average02 = this.checkNum(this.average02, 1, 59 - average01 || 0)
+			return average01 + '/' + average02;
 		},
 		// 计算勾选的checkbox值合集
 		checkboxString: function () {

+ 16 - 30
ruoyi-ui/src/components/Crontab/month.vue

@@ -9,16 +9,16 @@
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="2">
 				周期从
-				<el-input-number v-model='cycle01' :min="1" :max="12" /> -
-				<el-input-number v-model='cycle02' :min="1" :max="12" /> 月
+				<el-input-number v-model='cycle01' :min="1" :max="11" /> -
+				<el-input-number v-model='cycle02' :min="cycle01 ? cycle01 + 1 : 2" :max="12" /> 月
 			</el-radio>
 		</el-form-item>
 
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="3">
-				<el-input-number v-model='average01' :min="1" :max="12" /> 月开始,每
-				<el-input-number v-model='average02' :min="1" :max="12" /> 月月执行一次
+				<el-input-number v-model='average01' :min="1" :max="11" /> 月开始,每
+				<el-input-number v-model='average02' :min="1" :max="12 - average01 || 0" /> 月月执行一次
 			</el-radio>
 		</el-form-item>
 
@@ -51,29 +51,15 @@ export default {
 	methods: {
 		// 单选按钮值变化时
 		radioChange() {
-			if (this.radioValue === 1) {
-				this.$emit('update', 'month', '*');
-				this.$emit('update', 'year', '*');
-			} else {
-				if (this.cron.day === '*') {
-					this.$emit('update', 'day', '0', 'month');
-				}
-				if (this.cron.hour === '*') {
-					this.$emit('update', 'hour', '0', 'month');
-				}
-				if (this.cron.min === '*') {
-					this.$emit('update', 'min', '0', 'month');
-				}
-				if (this.cron.second === '*') {
-					this.$emit('update', 'second', '0', 'month');
-				}
-			}
 			switch (this.radioValue) {
+				case 1:
+					this.$emit('update', 'month', '*');
+					break;
 				case 2:
-					this.$emit('update', 'month', this.cycle01 + '-' + this.cycle02);
+					this.$emit('update', 'month', this.cycleTotal);
 					break;
 				case 3:
-					this.$emit('update', 'month', this.average01 + '/' + this.average02);
+					this.$emit('update', 'month', this.averageTotal);
 					break;
 				case 4:
 					this.$emit('update', 'month', this.checkboxString);
@@ -100,7 +86,7 @@ export default {
 		}
 	},
 	watch: {
-		"radioValue": "radioChange",
+		'radioValue': 'radioChange',
 		'cycleTotal': 'cycleChange',
 		'averageTotal': 'averageChange',
 		'checkboxString': 'checkboxChange'
@@ -108,15 +94,15 @@ export default {
 	computed: {
 		// 计算两个周期值
 		cycleTotal: function () {
-			this.cycle01 = this.checkNum(this.cycle01, 1, 12)
-			this.cycle02 = this.checkNum(this.cycle02, 1, 12)
-			return this.cycle01 + '-' + this.cycle02;
+			const cycle01 = this.checkNum(this.cycle01, 1, 11)
+			const cycle02 = this.checkNum(this.cycle02, cycle01 ? cycle01 + 1 : 2, 12)
+			return cycle01 + '-' + cycle02;
 		},
 		// 计算平均用到的值
 		averageTotal: function () {
-			this.average01 = this.checkNum(this.average01, 1, 12)
-			this.average02 = this.checkNum(this.average02, 1, 12)
-			return this.average01 + '/' + this.average02;
+			const average01 = this.checkNum(this.average01, 1, 11)
+			const average02 = this.checkNum(this.average02, 1, 12 - average01 || 0)
+			return average01 + '/' + average02;
 		},
 		// 计算勾选的checkbox值合集
 		checkboxString: function () {

+ 7 - 14
ruoyi-ui/src/components/Crontab/result.vue

@@ -179,7 +179,7 @@ export default {
 							// 获取达到条件的日期是星期X
 							let thisWeek = this.formatDate(new Date(YY + '-' + MM + '-' + thisDD + ' 00:00:00'), 'week');
 							// 当星期日时
-							if (thisWeek == 0) {
+							if (thisWeek == 1) {
 								// 先找下一个日,并判断是否为月底
 								DD++;
 								thisDD = DD < 10 ? '0' + DD : DD;
@@ -187,7 +187,7 @@ export default {
 								if (this.checkDate(YY + '-' + MM + '-' + thisDD + ' 00:00:00') !== true) {
 									DD -= 3;
 								}
-							} else if (thisWeek == 6) {
+							} else if (thisWeek == 7) {
 								// 当星期6时只需判断不是1号就可进行操作
 								if (this.dayRuleSup !== 1) {
 									DD--;
@@ -200,7 +200,7 @@ export default {
 							// 获取当前日期是属于星期几
 							let thisWeek = this.formatDate(new Date(YY + '-' + MM + '-' + DD + ' 00:00:00'), 'week');
 							// 校验当前星期是否在星期池(dayRuleSup)中
-							if (Array.indexOf(this.dayRuleSup, thisWeek) < 0) {
+							if (this.dayRuleSup.indexOf(thisWeek) < 0) {
 								// 如果到达最大值时
 								if (Di == DDate.length - 1) {
 									resetDay();
@@ -385,7 +385,7 @@ export default {
 				} else if (rule.indexOf('#') >= 0) {
 					this.dayRule = 'assWeek';
 					let matchRule = rule.match(/[0-9]{1}/g);
-					this.dayRuleSup = [Number(matchRule[0]), Number(matchRule[1])];
+					this.dayRuleSup = [Number(matchRule[1]), Number(matchRule[0])];
 					this.dateArr[3] = [1];
 					if (this.dayRuleSup[1] == 7) {
 						this.dayRuleSup[1] = 0;
@@ -401,14 +401,6 @@ export default {
 					this.dayRule = 'weekDay';
 					this.dayRuleSup = this.getAssignArr(rule)
 				}
-				// 如果weekDay时将7调整为0【week值0即是星期日】
-				if (this.dayRule == 'weekDay') {
-					for (let i = 0; i < this.dayRuleSup.length; i++) {
-						if (this.dayRuleSup[i] == 7) {
-							this.dayRuleSup[i] = 0;
-						}
-					}
-				}
 			}
 		},
 		// 获取"日"数组-少量为日期规则
@@ -543,14 +535,15 @@ export default {
 			if (type == undefined) {
 				return Y + '-' + (M < 10 ? '0' + M : M) + '-' + (D < 10 ? '0' + D : D) + ' ' + (h < 10 ? '0' + h : h) + ':' + (m < 10 ? '0' + m : m) + ':' + (s < 10 ? '0' + s : s);
 			} else if (type == 'week') {
-				return week;
+				// 在quartz中 1为星期日
+				return week + 1;
 			}
 		},
 		// 检查日期是否存在
 		checkDate(value) {
 			let time = new Date(value);
 			let format = this.formatDate(time)
-			return value == format ? true : false;
+			return value === format;
 		}
 	},
 	watch: {

+ 13 - 29
ruoyi-ui/src/components/Crontab/second.vue

@@ -9,16 +9,16 @@
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="2">
 				周期从
-				<el-input-number v-model='cycle01' :min="0" :max="60" /> -
-				<el-input-number v-model='cycle02' :min="0" :max="60" /> 秒
+				<el-input-number v-model='cycle01' :min="0" :max="58" /> -
+				<el-input-number v-model='cycle02' :min="cycle01 ? cycle01 + 1 : 1" :max="59" /> 秒
 			</el-radio>
 		</el-form-item>
 
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="3">
-				<el-input-number v-model='average01' :min="0" :max="60" /> 秒开始,每
-				<el-input-number v-model='average02' :min="0" :max="60" /> 秒执行一次
+				<el-input-number v-model='average01' :min="0" :max="58" /> 秒开始,每
+				<el-input-number v-model='average02' :min="1" :max="59 - average01 || 0" /> 秒执行一次
 			</el-radio>
 		</el-form-item>
 
@@ -54,13 +54,12 @@ export default {
 			switch (this.radioValue) {
 				case 1:
 					this.$emit('update', 'second', '*', 'second');
-					this.$emit('update', 'min', '*', 'second');
 					break;
 				case 2:
-					this.$emit('update', 'second', this.cycle01 + '-' + this.cycle02);
+					this.$emit('update', 'second', this.cycleTotal);
 					break;
 				case 3:
-					this.$emit('update', 'second', this.average01 + '/' + this.average02);
+					this.$emit('update', 'second', this.averageTotal);
 					break;
 				case 4:
 					this.$emit('update', 'second', this.checkboxString);
@@ -84,25 +83,10 @@ export default {
 			if (this.radioValue == '4') {
 				this.$emit('update', 'second', this.checkboxString);
 			}
-		},
-		othChange() {
-			// 反解析
-			let ins = this.cron.second
-			('反解析 second', ins);
-			if (ins === '*') {
-				this.radioValue = 1;
-			} else if (ins.indexOf('-') > -1) {
-				this.radioValue = 2
-			} else if (ins.indexOf('/') > -1) {
-				this.radioValue = 3
-			} else {
-				this.radioValue = 4
-				this.checkboxList = ins.split(',')
-			}
 		}
 	},
 	watch: {
-		"radioValue": "radioChange",
+		'radioValue': 'radioChange',
 		'cycleTotal': 'cycleChange',
 		'averageTotal': 'averageChange',
 		'checkboxString': 'checkboxChange',
@@ -113,15 +97,15 @@ export default {
 	computed: {
 		// 计算两个周期值
 		cycleTotal: function () {
-			this.cycle01 = this.checkNum(this.cycle01, 0, 59)
-			this.cycle02 = this.checkNum(this.cycle02, 0, 59)
-			return this.cycle01 + '-' + this.cycle02;
+			const cycle01 = this.checkNum(this.cycle01, 0, 58)
+			const cycle02 = this.checkNum(this.cycle02, cycle01 ? cycle01 + 1 : 1, 59)
+			return cycle01 + '-' + cycle02;
 		},
 		// 计算平均用到的值
 		averageTotal: function () {
-			this.average01 = this.checkNum(this.average01, 0, 59)
-			this.average02 = this.checkNum(this.average02, 1, 59)
-			return this.average01 + '/' + this.average02;
+			const average01 = this.checkNum(this.average01, 0, 58)
+			const average02 = this.checkNum(this.average02, 1, 59 - average01 || 0)
+			return average01 + '/' + average02;
 		},
 		// 计算勾选的checkbox值合集
 		checkboxString: function () {

+ 71 - 36
ruoyi-ui/src/components/Crontab/week.vue

@@ -2,7 +2,7 @@
 	<el-form size='small'>
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="1">
-				周,允许的通配符[, - * / L #]
+				周,允许的通配符[, - * ? / L #]
 			</el-radio>
 		</el-form-item>
 
@@ -15,8 +15,25 @@
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="3">
 				周期从星期
-				<el-input-number v-model='cycle01' :min="1" :max="7" /> -
-				<el-input-number v-model='cycle02' :min="1" :max="7" />
+				<el-select clearable v-model="cycle01">
+					<el-option
+						v-for="(item,index) of weekList"
+						:key="index"
+						:label="item.value"
+						:value="item.key"
+						:disabled="item.key === 1"
+					>{{item.value}}</el-option>
+				</el-select>
+				-
+				<el-select clearable v-model="cycle02">
+					<el-option
+						v-for="(item,index) of weekList"
+						:key="index"
+						:label="item.value"
+						:value="item.key"
+						:disabled="item.key < cycle01 && item.key !== 1"
+					>{{item.value}}</el-option>
+				</el-select>
 			</el-radio>
 		</el-form-item>
 
@@ -24,14 +41,18 @@
 			<el-radio v-model='radioValue' :label="4">
 				<el-input-number v-model='average01' :min="1" :max="4" /> 周的星期
-				<el-input-number v-model='average02' :min="1" :max="7" />
+				<el-select clearable v-model="average02">
+					<el-option v-for="(item,index) of weekList" :key="index" :label="item.value" :value="item.key">{{item.value}}</el-option>
+				</el-select>
 			</el-radio>
 		</el-form-item>
 
 		<el-form-item>
 			<el-radio v-model='radioValue' :label="5">
 				本月最后一个星期
-				<el-input-number v-model='weekday' :min="1" :max="7" />
+				<el-select clearable v-model="weekday">
+					<el-option v-for="(item,index) of weekList" :key="index" :label="item.value" :value="item.key">{{item.value}}</el-option>
+				</el-select>
 			</el-radio>
 		</el-form-item>
 
@@ -39,7 +60,7 @@
 			<el-radio v-model='radioValue' :label="6">
 				指定
 				<el-select clearable v-model="checkboxList" placeholder="可多选" multiple style="width:100%">
-					<el-option v-for="(item,index) of weekList" :key="index" :value="index+1">{{item}}</el-option>
+					<el-option v-for="(item,index) of weekList" :key="index" :label="item.value" :value="item.key">{{item.value}}</el-option>
 				</el-select>
 			</el-radio>
 		</el-form-item>
@@ -52,13 +73,42 @@ export default {
 	data() {
 		return {
 			radioValue: 2,
-			weekday: 1,
-			cycle01: 1,
-			cycle02: 2,
+			weekday: 2,
+			cycle01: 2,
+			cycle02: 3,
 			average01: 1,
-			average02: 1,
+			average02: 2,
 			checkboxList: [],
-			weekList: ['周一', '周二', '周三', '周四', '周五', '周六', '周日'],
+			weekList: [
+				{
+					key: 2,
+					value: '星期一'
+				},
+				{
+					key: 3,
+					value: '星期二'
+				},
+				{
+					key: 4,
+					value: '星期三'
+				},
+				{
+					key: 5,
+					value: '星期四'
+				},
+				{
+					key: 6,
+					value: '星期五'
+				},
+				{
+					key: 7,
+					value: '星期六'
+				},
+				{
+					key: 1,
+					value: '星期日'
+				}
+			],
 			checkNum: this.$options.propsData.check
 		}
 	},
@@ -67,45 +117,30 @@ export default {
 	methods: {
 		// 单选按钮值变化时
 		radioChange() {
-			if (this.radioValue === 1) {
-				this.$emit('update', 'week', '*');
-				this.$emit('update', 'year', '*');
-			} else {
-				if (this.cron.month === '*') {
-					this.$emit('update', 'month', '0', 'week');
-				}
-				if (this.cron.day === '*') {
-					this.$emit('update', 'day', '0', 'week');
-				}
-				if (this.cron.hour === '*') {
-					this.$emit('update', 'hour', '0', 'week');
-				}
-				if (this.cron.min === '*') {
-					this.$emit('update', 'min', '0', 'week');
-				}
-				if (this.cron.second === '*') {
-					this.$emit('update', 'second', '0', 'week');
-				}
+			if (this.radioValue !== 2 && this.cron.day !== '?') {
+				this.$emit('update', 'day', '?', 'week');
 			}
 			switch (this.radioValue) {
+				case 1:
+					this.$emit('update', 'week', '*');
+					break;
 				case 2:
 					this.$emit('update', 'week', '?');
 					break;
 				case 3:
-					this.$emit('update', 'week', this.cycle01 + '-' + this.cycle02);
+					this.$emit('update', 'week', this.cycleTotal);
 					break;
 				case 4:
-					this.$emit('update', 'week', this.average01 + '#' + this.average02);
+					this.$emit('update', 'week', this.averageTotal);
 					break;
 				case 5:
-					this.$emit('update', 'week', this.weekday + 'L');
+					this.$emit('update', 'week', this.weekdayCheck + 'L');
 					break;
 				case 6:
 					this.$emit('update', 'week', this.checkboxString);
 					break;
 			}
 		},
-		// 根据互斥事件,更改radio的值
 
 		// 周期两个值变化时
 		cycleChange() {
@@ -133,7 +168,7 @@ export default {
 		},
 	},
 	watch: {
-		"radioValue": "radioChange",
+		'radioValue': 'radioChange',
 		'cycleTotal': 'cycleChange',
 		'averageTotal': 'averageChange',
 		'weekdayCheck': 'weekdayChange',
@@ -150,7 +185,7 @@ export default {
 		averageTotal: function () {
 			this.average01 = this.checkNum(this.average01, 1, 4)
 			this.average02 = this.checkNum(this.average02, 1, 7)
-			return this.average01 + '#' + this.average02;
+			return this.average02 + '#' + this.average01;
 		},
 		// 最近的工作日(格式)
 		weekdayCheck: function () {

+ 15 - 28
ruoyi-ui/src/components/Crontab/year.vue

@@ -15,16 +15,16 @@
 		<el-form-item>
 			<el-radio :label="3" v-model='radioValue'>
 				周期从
-				<el-input-number v-model='cycle01' :min='fullYear' /> -
-				<el-input-number v-model='cycle02' :min='fullYear' />
+				<el-input-number v-model='cycle01' :min='fullYear' :max="2098" /> -
+				<el-input-number v-model='cycle02' :min="cycle01 ? cycle01 + 1 : fullYear + 1" :max="2099" />
 			</el-radio>
 		</el-form-item>
 
 		<el-form-item>
 			<el-radio :label="4" v-model='radioValue'>
-				<el-input-number v-model='average01' :min='fullYear' /> 年开始,每
-				<el-input-number v-model='average02' :min='fullYear' /> 年执行一次
+				<el-input-number v-model='average01' :min='fullYear' :max="2098"/> 年开始,每
+				<el-input-number v-model='average02' :min="1" :max="2099 - average01 || fullYear" /> 年执行一次
 			</el-radio>
 
 		</el-form-item>
@@ -59,21 +59,6 @@ export default {
 	methods: {
 		// 单选按钮值变化时
 		radioChange() {
-			if (this.cron.month === '*') {
-				this.$emit('update', 'month', '0', 'year');
-			}
-			if (this.cron.day === '*') {
-				this.$emit('update', 'day', '0', 'year');
-			}
-			if (this.cron.hour === '*') {
-				this.$emit('update', 'hour', '0', 'year');
-			}
-			if (this.cron.min === '*') {
-				this.$emit('update', 'min', '0', 'year');
-			}
-			if (this.cron.second === '*') {
-				this.$emit('update', 'second', '0', 'year');
-			}
 			switch (this.radioValue) {
 				case 1:
 					this.$emit('update', 'year', '');
@@ -82,10 +67,10 @@ export default {
 					this.$emit('update', 'year', '*');
 					break;
 				case 3:
-					this.$emit('update', 'year', this.cycle01 + '-' + this.cycle02);
+					this.$emit('update', 'year', this.cycleTotal);
 					break;
 				case 4:
-					this.$emit('update', 'year', this.average01 + '/' + this.average02);
+					this.$emit('update', 'year', this.averageTotal);
 					break;
 				case 5:
 					this.$emit('update', 'year', this.checkboxString);
@@ -112,7 +97,7 @@ export default {
 		}
 	},
 	watch: {
-		"radioValue": "radioChange",
+		'radioValue': 'radioChange',
 		'cycleTotal': 'cycleChange',
 		'averageTotal': 'averageChange',
 		'checkboxString': 'checkboxChange'
@@ -120,15 +105,15 @@ export default {
 	computed: {
 		// 计算两个周期值
 		cycleTotal: function () {
-			this.cycle01 = this.checkNum(this.cycle01, this.fullYear, this.fullYear + 100)
-			this.cycle02 = this.checkNum(this.cycle02, this.fullYear + 1, this.fullYear + 101)
-			return this.cycle01 + '-' + this.cycle02;
+			const cycle01 = this.checkNum(this.cycle01, this.fullYear, 2098)
+			const cycle02 = this.checkNum(this.cycle02, cycle01 ? cycle01 + 1 : this.fullYear + 1, 2099)
+			return cycle01 + '-' + cycle02;
 		},
 		// 计算平均用到的值
 		averageTotal: function () {
-			this.average01 = this.checkNum(this.average01, this.fullYear, this.fullYear + 100)
-			this.average02 = this.checkNum(this.average02, 1, 10)
-			return this.average01 + '/' + this.average02;
+			const average01 = this.checkNum(this.average01, this.fullYear, 2098)
+			const average02 = this.checkNum(this.average02, 1, 2099 - average01 || this.fullYear)
+			return average01 + '/' + average02;
 		},
 		// 计算勾选的checkbox值合集
 		checkboxString: function () {
@@ -139,6 +124,8 @@ export default {
 	mounted: function () {
 		// 仅获取当前年份
 		this.fullYear = Number(new Date().getFullYear());
+		this.cycle01 = this.fullYear
+		this.average01 = this.fullYear
 	}
 }
 </script>

+ 8 - 0
ruoyi-ui/src/plugins/modal.js

@@ -59,6 +59,14 @@ export default {
       type: "warning",
     })
   },
+  // 提交内容
+  prompt(content) {
+    return MessageBox.prompt(content, "系统提示", {
+      confirmButtonText: '确定',
+      cancelButtonText: '取消',
+      type: "warning",
+    })
+  },
   // 打开遮罩层
   loading(content) {
     loadingInstance = Loading.service({

+ 54 - 1
ruoyi-ui/src/views/index.vue

@@ -147,6 +147,59 @@
             <span>更新日志</span>
           </div>
           <el-collapse accordion>
+            <el-collapse-item title="v3.8.0 - 2021-12-01">
+              <ol>
+                <li>新增配套并同步的Vue3前端版本</li>
+                <li>新增通用方法简化模态/缓存/下载/权限/页签使用</li>
+                <li>优化导出数据/使用通用下载方法</li>
+                <li>Excel注解支持自定义数据处理器</li>
+                <li>Excel注解支持导入导出标题信息</li>
+                <li>Excel导入支持@Excels注解</li>
+                <li>新增组件data-dict,简化数据字典使用</li>
+                <li>新增Jaxb依赖,防止jdk8以上出现的兼容错误</li>
+                <li>生产环境使用路由懒加载提升页面响应速度</li>
+                <li>修复五级以上菜单出现的404问题</li>
+                <li>防重提交注解支持配置间隔时间/提示消息</li>
+                <li>日志注解新增是否保存响应参数</li>
+                <li>任务屏蔽违规字符&参数忽略双引号中的逗号</li>
+                <li>升级SpringBoot到最新版本2.5.6</li>
+                <li>升级pagehelper到最新版1.4.0</li>
+                <li>升级spring-boot-mybatis到最新版2.2.0</li>
+                <li>升级oshi到最新版本v5.8.2</li>
+                <li>升级druid到最新版1.2.8</li>
+                <li>升级velocity到最新版本2.3</li>
+                <li>升级fastjson到最新版1.2.78</li>
+                <li>升级axios到最新版本0.24.0</li>
+                <li>升级dart-sass到版本1.32.13</li>
+                <li>升级core-js到最新版本3.19.1</li>
+                <li>升级jsencrypt到最新版本3.2.1</li>
+                <li>升级js-cookie到最新版本3.0.1</li>
+                <li>升级file-saver到最新版本2.0.5</li>
+                <li>升级sass-loader到最新版本10.1.1</li>
+                <li>升级element-ui到最新版本2.15.6</li>
+                <li>新增sendGet无参请求方法</li>
+                <li>禁用el-tag组件的渐变动画</li>
+                <li>代码生成点击预览重置激活tab</li>
+                <li>AjaxResult重写put方法,以方便链式调用</li>
+                <li>优化登录/验证码请求headers不设置token</li>
+                <li>优化用户个人信息接口防止修改用户名</li>
+                <li>优化Cron表达式生成器关闭时销毁避免缓存</li>
+                <li>优化注册成功提示消息类型success</li>
+                <li>优化aop语法,使用spring自动注入注解</li>
+                <li>优化记录登录信息,移除不必要的修改</li>
+                <li>优化mybatis全局默认的执行器</li>
+                <li>优化Excel导入图片可能出现的异常</li>
+                <li>修复代码生成模板主子表删除缺少事务</li>
+                <li>修复日志记录可能出现的转换异常</li>
+                <li>修复代码生成复选框字典遗漏问题</li>
+                <li>修复关闭xss功能导致可重复读RepeatableFilter失效</li>
+                <li>修复字符串无法被反转义问题</li>
+                <li>修复后端主子表代码模板方法名生成错误问题</li>
+                <li>修复xss过滤后格式出现的异常</li>
+                <li>修复swagger没有指定dataTypeClass导致启动出现warn日志</li>
+                <li>其他细节优化</li>
+              </ol>
+            </el-collapse-item>
             <el-collapse-item title="v3.7.0 - 2021-09-13">
               <ol>
                 <li>参数管理支持配置验证码开关</li>
@@ -664,7 +717,7 @@ export default {
   data() {
     return {
       // 版本号
-      version: "3.7.0",
+      version: "3.8.0",
     };
   },
   methods: {

+ 1 - 1
ruoyi-ui/src/views/monitor/online/index.vue

@@ -111,7 +111,7 @@ export default {
     },
     /** 强退按钮操作 */
     handleForceLogout(row) {
-      this.$modal.confirm('是否确认强退名称为"' + row.userName + '"的数据项?').then(function() {
+      this.$modal.confirm('是否确认强退名称为"' + row.userName + '"的用户?').then(function() {
         return forceLogout(row.tokenId);
       }).then(() => {
         this.getList();

+ 1 - 1
ruoyi-ui/src/views/system/user/index.vue

@@ -596,7 +596,7 @@ export default {
         cancelButtonText: "取消",
         closeOnClickModal: false,
         inputPattern: /^.{5,20}$/,
-        inputErrorMessage: "用户密码长度必须介于 5 和 20 之间",
+        inputErrorMessage: "用户密码长度必须介于 5 和 20 之间"
       }).then(({ value }) => {
           resetUserPwd(row.userId, value).then(response => {
             this.$modal.msgSuccess("修改成功,新密码是:" + value);

+ 1 - 2
ruoyi-ui/src/views/tool/gen/basicInfoForm.vue

@@ -11,7 +11,6 @@
           <el-input placeholder="请输入" v-model="info.tableComment" />
         </el-form-item>
       </el-col>
-
       <el-col :span="12">
         <el-form-item label="实体类名称" prop="className">
           <el-input placeholder="请输入" v-model="info.className" />
@@ -30,9 +29,9 @@
     </el-row>
   </el-form>
 </template>
+
 <script>
 export default {
-  name: "BasicInfoForm",
   props: {
     info: {
       type: Object,

+ 1 - 0
ruoyi-ui/src/views/tool/gen/editTable.vue

@@ -124,6 +124,7 @@
     </el-form>
   </el-card>
 </template>
+
 <script>
 import { getGenTable, updateGenTable } from "@/api/tool/gen";
 import { optionselect as getDictOptionselect } from "@/api/system/dict/type";

+ 1 - 2
ruoyi-ui/src/views/tool/gen/genInfoForm.vue

@@ -11,7 +11,6 @@
           </el-select>
         </el-form-item>
       </el-col>
-
       <el-col :span="12">
         <el-form-item prop="packageName">
           <span slot="label">
@@ -213,12 +212,12 @@
     </el-row>
   </el-form>
 </template>
+
 <script>
 import Treeselect from "@riophae/vue-treeselect";
 import "@riophae/vue-treeselect/dist/vue-treeselect.css";
 
 export default {
-  name: "BasicInfoForm",
   components: { Treeselect },
   props: {
     info: {