From 3b6359caa04dd7a9483306d0539fc055dadf829b Mon Sep 17 00:00:00 2001 From: neilz Date: Sat, 13 Mar 2021 16:38:07 +0800 Subject: [PATCH 1/5] =?UTF-8?q?job=20=E5=8D=95=E5=85=83=E6=B5=8B=E8=AF=95?= =?UTF-8?q?=20Demo?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../controller/job/vo/job/InfJobBaseVO.java | 3 + .../service/job/impl/InfJobServiceImpl.java | 2 + .../infra/service/job/InfJobServiceTest.java | 78 +++++++++++++++++++ src/test/resources/sql/clean.sql | 1 + src/test/resources/sql/create_tables.sql | 18 +++++ 5 files changed, 102 insertions(+) create mode 100644 src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobServiceTest.java diff --git a/src/main/java/cn/iocoder/dashboard/modules/infra/controller/job/vo/job/InfJobBaseVO.java b/src/main/java/cn/iocoder/dashboard/modules/infra/controller/job/vo/job/InfJobBaseVO.java index 2df3ad823..352c490fc 100644 --- a/src/main/java/cn/iocoder/dashboard/modules/infra/controller/job/vo/job/InfJobBaseVO.java +++ b/src/main/java/cn/iocoder/dashboard/modules/infra/controller/job/vo/job/InfJobBaseVO.java @@ -34,4 +34,7 @@ public class InfJobBaseVO { @ApiModelProperty(value = "监控超时时间", example = "1000") private Integer monitorTimeout; + public void setCronExpression(String cronExpression) { + this.cronExpression = cronExpression; + } } diff --git a/src/main/java/cn/iocoder/dashboard/modules/infra/service/job/impl/InfJobServiceImpl.java b/src/main/java/cn/iocoder/dashboard/modules/infra/service/job/impl/InfJobServiceImpl.java index d82207de1..eab60051c 100644 --- a/src/main/java/cn/iocoder/dashboard/modules/infra/service/job/impl/InfJobServiceImpl.java +++ b/src/main/java/cn/iocoder/dashboard/modules/infra/service/job/impl/InfJobServiceImpl.java @@ -13,6 +13,7 @@ import cn.iocoder.dashboard.modules.infra.dal.mysql.job.InfJobMapper; import cn.iocoder.dashboard.modules.infra.enums.job.InfJobStatusEnum; import cn.iocoder.dashboard.modules.infra.service.job.InfJobService; import org.quartz.SchedulerException; +import org.springframework.boot.test.mock.mockito.MockBean; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import org.springframework.validation.annotation.Validated; @@ -37,6 +38,7 @@ public class InfJobServiceImpl implements InfJobService { @Resource private InfJobMapper jobMapper; + @MockBean @Resource private SchedulerManager schedulerManager; diff --git a/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobServiceTest.java b/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobServiceTest.java new file mode 100644 index 000000000..e8ed0dfc7 --- /dev/null +++ b/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobServiceTest.java @@ -0,0 +1,78 @@ +package cn.iocoder.dashboard.modules.infra.service.job; + +import static cn.iocoder.dashboard.util.AssertUtils.assertPojoEquals; +import static cn.iocoder.dashboard.util.RandomUtils.randomPojo; +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertNotNull; +import static org.mockito.Mockito.times; +import static org.mockito.Mockito.verify; + +import javax.annotation.Resource; + +import org.junit.jupiter.api.Test; +import org.quartz.SchedulerException; +import org.springframework.context.annotation.Import; +import cn.iocoder.dashboard.BaseDbUnitTest; +import cn.iocoder.dashboard.framework.quartz.core.scheduler.SchedulerManager; +import cn.iocoder.dashboard.modules.infra.controller.job.vo.job.InfJobCreateReqVO; +import cn.iocoder.dashboard.modules.infra.convert.job.InfJobConvert; +import cn.iocoder.dashboard.modules.infra.dal.dataobject.job.InfJobDO; +import cn.iocoder.dashboard.modules.infra.dal.mysql.job.InfJobMapper; +import cn.iocoder.dashboard.modules.infra.enums.job.InfJobStatusEnum; +import cn.iocoder.dashboard.modules.infra.service.job.impl.InfJobServiceImpl; + +/** + * {@link InfJobServiceImpl} 的单元测试 + * + * @author neilz + */ +@Import(InfJobServiceImpl.class) +public class InfJobServiceTest extends BaseDbUnitTest { + @Resource + private InfJobServiceImpl jobService; + + @Resource + private InfJobMapper jobMapper; + @Resource + private SchedulerManager schedulerManager; + + @Test + public void testCreateJob_success() throws SchedulerException { + // 准备参数 + InfJobCreateReqVO reqVO = randomPojo(InfJobCreateReqVO.class); + reqVO.setCronExpression("0 0/1 * * * ? *"); + + // 调用 + Long jobId = jobService.createJob(reqVO); + + // 断言 + assertNotNull(jobId); + + // 校验记录的属性是否正确 + InfJobDO job = jobMapper.selectById(jobId); + assertPojoEquals(reqVO, job); + assertEquals(InfJobStatusEnum.NORMAL.getStatus(), job.getStatus()); + + // 校验调用 + verify(jobMapper, times(1)).selectByHandlerName(reqVO.getHandlerName()); + + InfJobDO insertJob = InfJobConvert.INSTANCE.convert(reqVO); + insertJob.setStatus(InfJobStatusEnum.INIT.getStatus()); + fillJobMonitorTimeoutEmpty(insertJob); + verify(jobMapper, times(1)).insert(insertJob); + + verify(schedulerManager, times(1)).addJob(job.getId(), job.getHandlerName(), job.getHandlerParam(), job.getCronExpression(), + job.getRetryCount(), job.getRetryInterval()); + + InfJobDO updateObj = InfJobDO.builder().id(insertJob.getId()).status(InfJobStatusEnum.NORMAL.getStatus()).build(); + verify(jobMapper, times(1)).updateById(updateObj); + + } + + private static void fillJobMonitorTimeoutEmpty(InfJobDO job) { + if (job.getMonitorTimeout() == null) { + job.setMonitorTimeout(0); + } + } + +} diff --git a/src/test/resources/sql/clean.sql b/src/test/resources/sql/clean.sql index 75372fd1a..329a94064 100644 --- a/src/test/resources/sql/clean.sql +++ b/src/test/resources/sql/clean.sql @@ -1,6 +1,7 @@ -- inf 开头的 DB DELETE FROM "inf_config"; DELETE FROM "inf_file"; +DELETE FROM "inf_job"; -- sys 开头的 DB DELETE FROM "sys_dept"; diff --git a/src/test/resources/sql/create_tables.sql b/src/test/resources/sql/create_tables.sql index 36c573dd9..f4908a710 100644 --- a/src/test/resources/sql/create_tables.sql +++ b/src/test/resources/sql/create_tables.sql @@ -29,6 +29,24 @@ CREATE TABLE IF NOT EXISTS "inf_file" ( PRIMARY KEY ("id") ) COMMENT '文件表'; +CREATE TABLE "inf_job" ( + "id" bigint(20) NOT NULL GENERATED BY DEFAULT AS IDENTITY COMMENT '任务编号', + "name" varchar(32) NOT NULL COMMENT '任务名称', + "status" tinyint(4) NOT NULL COMMENT '任务状态', + "handler_name" varchar(64) NOT NULL COMMENT '处理器的名字', + "handler_param" varchar(255) DEFAULT NULL COMMENT '处理器的参数', + "cron_expression" varchar(32) NOT NULL COMMENT 'CRON 表达式', + "retry_count" int(11) NOT NULL DEFAULT '0' COMMENT '重试次数', + "retry_interval" int(11) NOT NULL DEFAULT '0' COMMENT '重试间隔', + "monitor_timeout" int(11) NOT NULL DEFAULT '0' COMMENT '监控超时时间', + "creator" varchar(64) DEFAULT '' COMMENT '创建者', + "create_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间', + "updater" varchar(64) DEFAULT '' COMMENT '更新者', + "update_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间', + "deleted" bit(1) NOT NULL DEFAULT b'0' COMMENT '是否删除', + PRIMARY KEY ("id") +) COMMENT='定时任务表'; + -- sys 开头的 DB CREATE TABLE IF NOT EXISTS "sys_dept" ( From dd8b6cc94a460e5780c8029e9a920cece8bb0036 Mon Sep 17 00:00:00 2001 From: YunaiV Date: Sat, 13 Mar 2021 19:58:11 +0800 Subject: [PATCH 2/5] =?UTF-8?q?1.=20=E5=A2=9E=E5=8A=A0=E4=BA=8B=E5=8A=A1?= =?UTF-8?q?=E7=AE=A1=E7=90=86=E5=99=A8=E7=9A=84=E8=87=AA=E5=8A=A8=E9=85=8D?= =?UTF-8?q?=E7=BD=AE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/test/java/cn/iocoder/dashboard/BaseDbAndRedisUnitTest.java | 2 ++ src/test/java/cn/iocoder/dashboard/BaseDbUnitTest.java | 2 ++ 2 files changed, 4 insertions(+) diff --git a/src/test/java/cn/iocoder/dashboard/BaseDbAndRedisUnitTest.java b/src/test/java/cn/iocoder/dashboard/BaseDbAndRedisUnitTest.java index 59bacb052..aadf47bda 100644 --- a/src/test/java/cn/iocoder/dashboard/BaseDbAndRedisUnitTest.java +++ b/src/test/java/cn/iocoder/dashboard/BaseDbAndRedisUnitTest.java @@ -9,6 +9,7 @@ import com.baomidou.mybatisplus.autoconfigure.MybatisPlusAutoConfiguration; import org.redisson.spring.starter.RedissonAutoConfiguration; import org.springframework.boot.autoconfigure.data.redis.RedisAutoConfiguration; import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration; +import org.springframework.boot.autoconfigure.jdbc.DataSourceTransactionManagerAutoConfiguration; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.context.annotation.Import; import org.springframework.test.context.ActiveProfiles; @@ -30,6 +31,7 @@ public class BaseDbAndRedisUnitTest { // DB 配置类 DataSourceConfiguration.class, // 自己的 DB 配置类 DataSourceAutoConfiguration.class, // Spring DB 自动配置类 + DataSourceTransactionManagerAutoConfiguration.class, // Spring 事务自动配置类 DruidDataSourceAutoConfigure.class, // Druid 自动配置类 // MyBatis 配置类 MybatisConfiguration.class, // 自己的 MyBatis 配置类 diff --git a/src/test/java/cn/iocoder/dashboard/BaseDbUnitTest.java b/src/test/java/cn/iocoder/dashboard/BaseDbUnitTest.java index 821118279..19e930f1a 100644 --- a/src/test/java/cn/iocoder/dashboard/BaseDbUnitTest.java +++ b/src/test/java/cn/iocoder/dashboard/BaseDbUnitTest.java @@ -5,6 +5,7 @@ import cn.iocoder.dashboard.framework.mybatis.config.MybatisConfiguration; import com.alibaba.druid.spring.boot.autoconfigure.DruidDataSourceAutoConfigure; import com.baomidou.mybatisplus.autoconfigure.MybatisPlusAutoConfiguration; import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration; +import org.springframework.boot.autoconfigure.jdbc.DataSourceTransactionManagerAutoConfiguration; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.context.annotation.Import; import org.springframework.test.context.ActiveProfiles; @@ -26,6 +27,7 @@ public class BaseDbUnitTest { // DB 配置类 DataSourceConfiguration.class, // 自己的 DB 配置类 DataSourceAutoConfiguration.class, // Spring DB 自动配置类 + DataSourceTransactionManagerAutoConfiguration.class, // Spring 事务自动配置类 DruidDataSourceAutoConfigure.class, // Druid 自动配置类 // MyBatis 配置类 MybatisConfiguration.class, // 自己的 MyBatis 配置类 From 0775e85aacf544343b608ea889b5e5da149bd572 Mon Sep 17 00:00:00 2001 From: neilz Date: Sun, 14 Mar 2021 15:35:42 +0800 Subject: [PATCH 3/5] =?UTF-8?q?Quartz=20=E7=9B=B8=E5=85=B3=E8=A1=A8?= =?UTF-8?q?=E6=96=B0=E5=A2=9E=E5=88=9D=E5=A7=8B=E5=8C=96=E4=BB=BB=E5=8A=A1?= =?UTF-8?q?sql=20sysUserSessionTimeoutJob?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- sql/quartz.sql | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/sql/quartz.sql b/sql/quartz.sql index dca0859e1..cf5ee70d7 100644 --- a/sql/quartz.sql +++ b/sql/quartz.sql @@ -178,3 +178,11 @@ CREATE INDEX IDX_QRTZ_FT_T_G ON QRTZ_FIRED_TRIGGERS(SCHED_NAME,TRIGGER_NAME,TRIG CREATE INDEX IDX_QRTZ_FT_TG ON QRTZ_FIRED_TRIGGERS(SCHED_NAME,TRIGGER_GROUP); commit; + +-- 初始化默认任务 用户 Session 超时 Job +INSERT INTO QRTZ_JOB_DETAILS VALUES ('schedulerName', 'sysUserSessionTimeoutJob', 'DEFAULT', NULL, 'cn.iocoder.dashboard.framework.quartz.core.handler.JobHandlerInvoker', '0', '1', '1', '0', 0xACED0005737200156F72672E71756172747A2E4A6F62446174614D61709FB083E8BFA9B0CB020000787200266F72672E71756172747A2E7574696C732E537472696E674B65794469727479466C61674D61708208E8C3FBC55D280200015A0013616C6C6F77735472616E7369656E74446174617872001D6F72672E71756172747A2E7574696C732E4469727479466C61674D617013E62EAD28760ACE0200025A000564697274794C00036D617074000F4C6A6176612F7574696C2F4D61703B787001737200116A6176612E7574696C2E486173684D61700507DAC1C31660D103000246000A6C6F6164466163746F724900097468726573686F6C6478703F4000000000000C770800000010000000027400064A4F425F49447372000E6A6176612E6C616E672E4C6F6E673B8BE490CC8F23DF0200014A000576616C7565787200106A6176612E6C616E672E4E756D62657286AC951D0B94E08B020000787000000000000000047400104A4F425F48414E444C45525F4E414D457400187379735573657253657373696F6E54696D656F75744A6F627800); +commit; +INSERT INTO QRTZ_TRIGGERS VALUES ('schedulerName', 'sysUserSessionTimeoutJob', 'DEFAULT', 'sysUserSessionTimeoutJob', 'DEFAULT', NULL, 1615706340000, 1615706280000, 5, 'WAITING', 'CRON', 1615706125000, 0, NULL, 0, 0xACED0005737200156F72672E71756172747A2E4A6F62446174614D61709FB083E8BFA9B0CB020000787200266F72672E71756172747A2E7574696C732E537472696E674B65794469727479466C61674D61708208E8C3FBC55D280200015A0013616C6C6F77735472616E7369656E74446174617872001D6F72672E71756172747A2E7574696C732E4469727479466C61674D617013E62EAD28760ACE0200025A000564697274794C00036D617074000F4C6A6176612F7574696C2F4D61703B787001737200116A6176612E7574696C2E486173684D61700507DAC1C31660D103000246000A6C6F6164466163746F724900097468726573686F6C6478703F4000000000000C770800000010000000037400114A4F425F48414E444C45525F504152414D707400124A4F425F52455452595F494E54455256414C737200116A6176612E6C616E672E496E746567657212E2A0A4F781873802000149000576616C7565787200106A6176612E6C616E672E4E756D62657286AC951D0B94E08B0200007870000007D074000F4A4F425F52455452595F434F554E547371007E0009000000037800); +commit; +INSERT INTO QRTZ_CRON_TRIGGERS VALUES ('schedulerName', 'sysUserSessionTimeoutJob', 'DEFAULT', '0 * * * * ? *', 'Asia/Shanghai'); +commit; From ca1132f2df07a1c9e04379f75a7cb21f0e243cdc Mon Sep 17 00:00:00 2001 From: neilz Date: Sun, 14 Mar 2021 20:59:40 +0800 Subject: [PATCH 4/5] =?UTF-8?q?job=20=E5=8D=95=E5=85=83=E6=B5=8B=E8=AF=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../service/job/impl/InfJobServiceImpl.java | 2 - .../service/job/InfJobLogServiceTest.java | 173 ++++++++++++ .../infra/service/job/InfJobServiceTest.java | 249 ++++++++++++++++-- src/test/resources/sql/clean.sql | 1 + src/test/resources/sql/create_tables.sql | 52 ++-- 5 files changed, 439 insertions(+), 38 deletions(-) create mode 100644 src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobLogServiceTest.java diff --git a/src/main/java/cn/iocoder/dashboard/modules/infra/service/job/impl/InfJobServiceImpl.java b/src/main/java/cn/iocoder/dashboard/modules/infra/service/job/impl/InfJobServiceImpl.java index 3cdbbf1c9..156c423c6 100644 --- a/src/main/java/cn/iocoder/dashboard/modules/infra/service/job/impl/InfJobServiceImpl.java +++ b/src/main/java/cn/iocoder/dashboard/modules/infra/service/job/impl/InfJobServiceImpl.java @@ -13,7 +13,6 @@ import cn.iocoder.dashboard.modules.infra.dal.mysql.job.InfJobMapper; import cn.iocoder.dashboard.modules.infra.enums.job.InfJobStatusEnum; import cn.iocoder.dashboard.modules.infra.service.job.InfJobService; import org.quartz.SchedulerException; -import org.springframework.boot.test.mock.mockito.MockBean; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import org.springframework.validation.annotation.Validated; @@ -38,7 +37,6 @@ public class InfJobServiceImpl implements InfJobService { @Resource private InfJobMapper jobMapper; - @MockBean @Resource private SchedulerManager schedulerManager; diff --git a/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobLogServiceTest.java b/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobLogServiceTest.java new file mode 100644 index 000000000..d6caa2a54 --- /dev/null +++ b/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobLogServiceTest.java @@ -0,0 +1,173 @@ +package cn.iocoder.dashboard.modules.infra.service.job; + +import static cn.hutool.core.util.RandomUtil.randomEle; +import static cn.iocoder.dashboard.util.AssertUtils.assertPojoEquals; +import static cn.iocoder.dashboard.util.RandomUtils.randomLongId; +import static cn.iocoder.dashboard.util.RandomUtils.randomPojo; +import static cn.iocoder.dashboard.util.RandomUtils.randomString; +import static cn.iocoder.dashboard.util.date.DateUtils.buildTime; +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertNotNull; + +import java.util.ArrayList; +import java.util.List; + +import javax.annotation.Resource; + +import org.junit.jupiter.api.Test; +import org.springframework.context.annotation.Import; + +import cn.iocoder.dashboard.BaseDbUnitTest; +import cn.iocoder.dashboard.common.pojo.PageResult; +import cn.iocoder.dashboard.modules.infra.controller.job.vo.log.InfJobLogExportReqVO; +import cn.iocoder.dashboard.modules.infra.controller.job.vo.log.InfJobLogPageReqVO; +import cn.iocoder.dashboard.modules.infra.dal.dataobject.job.InfJobLogDO; +import cn.iocoder.dashboard.modules.infra.dal.mysql.job.InfJobLogMapper; +import cn.iocoder.dashboard.modules.infra.enums.job.InfJobLogStatusEnum; +import cn.iocoder.dashboard.modules.infra.service.job.impl.InfJobLogServiceImpl; +import cn.iocoder.dashboard.util.object.ObjectUtils; + +/** + * {@link InfJobLogServiceImpl} 的单元测试 + * + * @author neilz + */ +@Import(InfJobLogServiceImpl.class) +public class InfJobLogServiceTest extends BaseDbUnitTest { + + @Resource + private InfJobLogServiceImpl jobLogService; + @Resource + private InfJobLogMapper jobLogMapper; + + @Test + public void testCreateJobLog_success() { + // 准备参数 + InfJobLogDO reqVO = randomPojo(InfJobLogDO.class, o -> { + o.setExecuteIndex(1); + }); + // 调用 + Long jobLogId = jobLogService.createJobLog(reqVO.getJobId(), reqVO.getBeginTime(), reqVO.getHandlerName(), reqVO.getHandlerParam(), reqVO.getExecuteIndex()); + // 断言 + assertNotNull(jobLogId); + // 校验记录的属性是否正确 + InfJobLogDO job = jobLogMapper.selectById(jobLogId); + assertEquals(InfJobLogStatusEnum.RUNNING.getStatus(), job.getStatus()); + } + + @Test + public void testUpdateJobLogResultAsync_success() { + // 准备参数 + InfJobLogDO reqVO = randomPojo(InfJobLogDO.class, o -> { + o.setExecuteIndex(1); + }); + InfJobLogDO log = InfJobLogDO.builder().jobId(reqVO.getJobId()).handlerName(reqVO.getHandlerName()).handlerParam(reqVO.getHandlerParam()).executeIndex(reqVO.getExecuteIndex()) + .beginTime(reqVO.getBeginTime()).status(InfJobLogStatusEnum.RUNNING.getStatus()).build(); + jobLogMapper.insert(log); + // 调用 + jobLogService.updateJobLogResultAsync(log.getId(), reqVO.getBeginTime(), reqVO.getDuration(), true,reqVO.getResult()); + // 校验记录的属性是否正确 + InfJobLogDO job = jobLogMapper.selectById(log.getId()); + assertEquals(InfJobLogStatusEnum.SUCCESS.getStatus(), job.getStatus()); + + // 调用 + jobLogService.updateJobLogResultAsync(log.getId(), reqVO.getBeginTime(), reqVO.getDuration(), false,reqVO.getResult()); + // 校验记录的属性是否正确 + InfJobLogDO job2 = jobLogMapper.selectById(log.getId()); + assertEquals(InfJobLogStatusEnum.FAILURE.getStatus(), job2.getStatus()); + } + + @Test + public void testGetJobLogListByIds_success() { + // mock 数据 + InfJobLogDO dbJobLog = randomPojo(InfJobLogDO.class, o -> { + o.setExecuteIndex(1); + o.setStatus(randomEle(InfJobLogStatusEnum.values()).getStatus()); // 保证 status 的范围 + }); + InfJobLogDO cloneJobLog = ObjectUtils.clone(dbJobLog, o -> o.setHandlerName(randomString())); + jobLogMapper.insert(dbJobLog); + // 测试 handlerName 不匹配 + jobLogMapper.insert(cloneJobLog); + // 准备参数 + ArrayList ids = new ArrayList<>(); + ids.add(dbJobLog.getId()); + ids.add(cloneJobLog.getId()); + // 调用 + List list = jobLogService.getJobLogList(ids); + // 断言 + assertEquals(2, list.size()); + assertPojoEquals(dbJobLog, list.get(0)); + } + + @Test + public void testGetJobPage_success() { + // mock 数据 + InfJobLogDO dbJobLog = randomPojo(InfJobLogDO.class, o -> { + o.setExecuteIndex(1); + o.setHandlerName("handlerName 单元测试"); + o.setStatus(InfJobLogStatusEnum.SUCCESS.getStatus()); + o.setBeginTime(buildTime(2021, 1, 8)); + o.setEndTime(buildTime(2021, 1, 8)); + }); + jobLogMapper.insert(dbJobLog); + // 测试 jobId 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setJobId(randomLongId()))); + // 测试 handlerName 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setHandlerName(randomString()))); + // 测试 beginTime 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setBeginTime(buildTime(2021, 1, 7)))); + // 测试 endTime 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setEndTime(buildTime(2021, 1, 9)))); + // 测试 status 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setStatus(InfJobLogStatusEnum.FAILURE.getStatus()))); + // 准备参数 + InfJobLogPageReqVO reqVo = new InfJobLogPageReqVO(); + reqVo.setJobId(dbJobLog.getJobId()); + reqVo.setHandlerName("单元"); + reqVo.setBeginTime(dbJobLog.getBeginTime()); + reqVo.setEndTime(dbJobLog.getEndTime()); + reqVo.setStatus(InfJobLogStatusEnum.SUCCESS.getStatus()); + // 调用 + PageResult pageResult = jobLogService.getJobLogPage(reqVo); + // 断言 + assertEquals(1, pageResult.getTotal()); + assertEquals(1, pageResult.getList().size()); + assertPojoEquals(dbJobLog, pageResult.getList().get(0)); + } + + @Test + public void testGetJobListForExport_success() { + // mock 数据 + InfJobLogDO dbJobLog = randomPojo(InfJobLogDO.class, o -> { + o.setExecuteIndex(1); + o.setHandlerName("handlerName 单元测试"); + o.setStatus(InfJobLogStatusEnum.SUCCESS.getStatus()); + o.setBeginTime(buildTime(2021, 1, 8)); + o.setEndTime(buildTime(2021, 1, 8)); + }); + jobLogMapper.insert(dbJobLog); + // 测试 jobId 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setJobId(randomLongId()))); + // 测试 handlerName 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setHandlerName(randomString()))); + // 测试 beginTime 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setBeginTime(buildTime(2021, 1, 7)))); + // 测试 endTime 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setEndTime(buildTime(2021, 1, 9)))); + // 测试 status 不匹配 + jobLogMapper.insert(ObjectUtils.clone(dbJobLog, o -> o.setStatus(InfJobLogStatusEnum.FAILURE.getStatus()))); + // 准备参数 + InfJobLogExportReqVO reqVo = new InfJobLogExportReqVO(); + reqVo.setJobId(dbJobLog.getJobId()); + reqVo.setHandlerName("单元"); + reqVo.setBeginTime(dbJobLog.getBeginTime()); + reqVo.setEndTime(dbJobLog.getEndTime()); + reqVo.setStatus(InfJobLogStatusEnum.SUCCESS.getStatus()); + // 调用 + List list = jobLogService.getJobLogList(reqVo); + // 断言 + assertEquals(1, list.size()); + assertPojoEquals(dbJobLog, list.get(0)); + } + +} diff --git a/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobServiceTest.java b/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobServiceTest.java index e8ed0dfc7..10a2dba7a 100644 --- a/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobServiceTest.java +++ b/src/test/java/cn/iocoder/dashboard/modules/infra/service/job/InfJobServiceTest.java @@ -1,25 +1,43 @@ package cn.iocoder.dashboard.modules.infra.service.job; +import static cn.hutool.core.util.RandomUtil.randomEle; +import static cn.iocoder.dashboard.modules.infra.enums.InfErrorCodeConstants.JOB_CHANGE_STATUS_EQUALS; +import static cn.iocoder.dashboard.modules.infra.enums.InfErrorCodeConstants.JOB_CHANGE_STATUS_INVALID; +import static cn.iocoder.dashboard.modules.infra.enums.InfErrorCodeConstants.JOB_CRON_EXPRESSION_VALID; +import static cn.iocoder.dashboard.modules.infra.enums.InfErrorCodeConstants.JOB_HANDLER_EXISTS; +import static cn.iocoder.dashboard.modules.infra.enums.InfErrorCodeConstants.JOB_NOT_EXISTS; +import static cn.iocoder.dashboard.modules.infra.enums.InfErrorCodeConstants.JOB_UPDATE_ONLY_NORMAL_STATUS; import static cn.iocoder.dashboard.util.AssertUtils.assertPojoEquals; +import static cn.iocoder.dashboard.util.AssertUtils.assertServiceException; import static cn.iocoder.dashboard.util.RandomUtils.randomPojo; +import static cn.iocoder.dashboard.util.RandomUtils.randomString; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNotNull; -import static org.mockito.Mockito.times; -import static org.mockito.Mockito.verify; +import static org.junit.jupiter.api.Assertions.assertNull; + +import java.util.ArrayList; +import java.util.List; import javax.annotation.Resource; import org.junit.jupiter.api.Test; import org.quartz.SchedulerException; +import org.springframework.boot.test.mock.mockito.MockBean; import org.springframework.context.annotation.Import; + import cn.iocoder.dashboard.BaseDbUnitTest; +import cn.iocoder.dashboard.common.pojo.PageResult; import cn.iocoder.dashboard.framework.quartz.core.scheduler.SchedulerManager; import cn.iocoder.dashboard.modules.infra.controller.job.vo.job.InfJobCreateReqVO; +import cn.iocoder.dashboard.modules.infra.controller.job.vo.job.InfJobExportReqVO; +import cn.iocoder.dashboard.modules.infra.controller.job.vo.job.InfJobPageReqVO; +import cn.iocoder.dashboard.modules.infra.controller.job.vo.job.InfJobUpdateReqVO; import cn.iocoder.dashboard.modules.infra.convert.job.InfJobConvert; import cn.iocoder.dashboard.modules.infra.dal.dataobject.job.InfJobDO; import cn.iocoder.dashboard.modules.infra.dal.mysql.job.InfJobMapper; import cn.iocoder.dashboard.modules.infra.enums.job.InfJobStatusEnum; import cn.iocoder.dashboard.modules.infra.service.job.impl.InfJobServiceImpl; +import cn.iocoder.dashboard.util.object.ObjectUtils; /** * {@link InfJobServiceImpl} 的单元测试 @@ -28,45 +46,236 @@ import cn.iocoder.dashboard.modules.infra.service.job.impl.InfJobServiceImpl; */ @Import(InfJobServiceImpl.class) public class InfJobServiceTest extends BaseDbUnitTest { - @Resource - private InfJobServiceImpl jobService; @Resource - private InfJobMapper jobMapper; + private InfJobServiceImpl jobService; @Resource + private InfJobMapper jobMapper; + @MockBean private SchedulerManager schedulerManager; @Test - public void testCreateJob_success() throws SchedulerException { - // 准备参数 + public void testCreateJob_cronExpressionValid() { + // 准备参数。Cron 表达式为 String 类型,默认随机字符串。 InfJobCreateReqVO reqVO = randomPojo(InfJobCreateReqVO.class); - reqVO.setCronExpression("0 0/1 * * * ? *"); + // 调用,并断言异常 + assertServiceException(() -> jobService.createJob(reqVO), JOB_CRON_EXPRESSION_VALID); + } + @Test + public void testCreateJob_jobHandlerExists() throws SchedulerException { + // 准备参数 指定 Cron 表达式 + InfJobCreateReqVO reqVO = randomPojo(InfJobCreateReqVO.class, o -> o.setCronExpression("0 0/1 * * * ? *")); + // 调用 + jobService.createJob(reqVO); + // 调用,并断言异常 + assertServiceException(() -> jobService.createJob(reqVO), JOB_HANDLER_EXISTS); + } + + @Test + public void testCreateJob_success() throws SchedulerException { + // 准备参数 指定 Cron 表达式 + InfJobCreateReqVO reqVO = randomPojo(InfJobCreateReqVO.class, o -> o.setCronExpression("0 0/1 * * * ? *")); // 调用 Long jobId = jobService.createJob(reqVO); - // 断言 assertNotNull(jobId); - // 校验记录的属性是否正确 InfJobDO job = jobMapper.selectById(jobId); assertPojoEquals(reqVO, job); assertEquals(InfJobStatusEnum.NORMAL.getStatus(), job.getStatus()); + } - // 校验调用 - verify(jobMapper, times(1)).selectByHandlerName(reqVO.getHandlerName()); + @Test + public void testUpdateJob_jobNotExists(){ + // 准备参数 + InfJobUpdateReqVO reqVO = randomPojo(InfJobUpdateReqVO.class, o -> o.setCronExpression("0 0/1 * * * ? *")); + // 调用,并断言异常 + assertServiceException(() -> jobService.updateJob(reqVO), JOB_NOT_EXISTS); + } - InfJobDO insertJob = InfJobConvert.INSTANCE.convert(reqVO); - insertJob.setStatus(InfJobStatusEnum.INIT.getStatus()); - fillJobMonitorTimeoutEmpty(insertJob); - verify(jobMapper, times(1)).insert(insertJob); + @Test + public void testUpdateJob_onlyNormalStatus(){ + // mock 数据 + InfJobCreateReqVO createReqVO = randomPojo(InfJobCreateReqVO.class, o -> o.setCronExpression("0 0/1 * * * ? *")); + InfJobDO job = InfJobConvert.INSTANCE.convert(createReqVO); + job.setStatus(InfJobStatusEnum.INIT.getStatus()); + fillJobMonitorTimeoutEmpty(job); + jobMapper.insert(job); + // 准备参数 + InfJobUpdateReqVO updateReqVO = randomPojo(InfJobUpdateReqVO.class, o -> { + o.setId(job.getId()); + o.setName(createReqVO.getName()); + o.setCronExpression(createReqVO.getCronExpression()); + }); + // 调用,并断言异常 + assertServiceException(() -> jobService.updateJob(updateReqVO), JOB_UPDATE_ONLY_NORMAL_STATUS); + } - verify(schedulerManager, times(1)).addJob(job.getId(), job.getHandlerName(), job.getHandlerParam(), job.getCronExpression(), - job.getRetryCount(), job.getRetryInterval()); + @Test + public void testUpdateJob_success() throws SchedulerException { + // mock 数据 + InfJobCreateReqVO createReqVO = randomPojo(InfJobCreateReqVO.class, o -> o.setCronExpression("0 0/1 * * * ? *")); + InfJobDO job = InfJobConvert.INSTANCE.convert(createReqVO); + job.setStatus(InfJobStatusEnum.NORMAL.getStatus()); + fillJobMonitorTimeoutEmpty(job); + jobMapper.insert(job); + schedulerManager.addJob(job.getId(), job.getHandlerName(), job.getHandlerParam(), job.getCronExpression(), + createReqVO.getRetryCount(), createReqVO.getRetryInterval()); + // 准备参数 + InfJobUpdateReqVO updateReqVO = randomPojo(InfJobUpdateReqVO.class, o -> { + o.setId(job.getId()); + o.setName(createReqVO.getName()); + o.setCronExpression(createReqVO.getCronExpression()); + }); + // 调用 + jobService.updateJob(updateReqVO); + // 校验记录的属性是否正确 + InfJobDO updateJob = jobMapper.selectById(updateReqVO.getId()); + assertPojoEquals(updateReqVO, updateJob); + } - InfJobDO updateObj = InfJobDO.builder().id(insertJob.getId()).status(InfJobStatusEnum.NORMAL.getStatus()).build(); - verify(jobMapper, times(1)).updateById(updateObj); + @Test + public void testUpdateJobStatus_changeStatusInvalid() { + // 调用,并断言异常 + assertServiceException(() -> jobService.updateJobStatus(1l, InfJobStatusEnum.INIT.getStatus()), JOB_CHANGE_STATUS_INVALID); + } + @Test + public void testUpdateJobStatus_changeStatusEquals() { + // mock 数据 + InfJobCreateReqVO createReqVO = randomPojo(InfJobCreateReqVO.class, o -> o.setCronExpression("0 0/1 * * * ? *")); + InfJobDO job = InfJobConvert.INSTANCE.convert(createReqVO); + job.setStatus(InfJobStatusEnum.NORMAL.getStatus()); + fillJobMonitorTimeoutEmpty(job); + jobMapper.insert(job); + // 调用,并断言异常 + assertServiceException(() -> jobService.updateJobStatus(job.getId(), job.getStatus()), JOB_CHANGE_STATUS_EQUALS); + } + + @Test + public void testUpdateJobStatus_success() throws SchedulerException { + // mock 数据 + InfJobCreateReqVO createReqVO = randomPojo(InfJobCreateReqVO.class, o -> o.setCronExpression("0 0/1 * * * ? *")); + InfJobDO job = InfJobConvert.INSTANCE.convert(createReqVO); + job.setStatus(InfJobStatusEnum.NORMAL.getStatus()); + fillJobMonitorTimeoutEmpty(job); + jobMapper.insert(job); + schedulerManager.addJob(job.getId(), job.getHandlerName(), job.getHandlerParam(), job.getCronExpression(), + createReqVO.getRetryCount(), createReqVO.getRetryInterval()); + // 调用 + jobService.updateJobStatus(job.getId(), InfJobStatusEnum.STOP.getStatus()); + // 校验记录的属性是否正确 + InfJobDO updateJob = jobMapper.selectById(job.getId()); + assertEquals(InfJobStatusEnum.STOP.getStatus(), updateJob.getStatus()); + } + + /** + * 页面"执行一次"按钮功能集成测试发现问题: + * inf_job 表初始化任务 sysUserSessionTimeoutJob 点击报错,是因为 Job 并没有添加到 Quartz 中; + * 没有走 createJob 中 scheduler.scheduleJob() 这一步,报错任务找不到。 + * // FINISHED Quartz 相关表新增初始化任务 sysUserSessionTimeoutJob sql + */ + @Test + public void testTriggerJob_success() throws SchedulerException { + /** + * TODO 不知道是否要将 Quartz 相关 SQL 引入来做单元测试 + * 1、schedulerManager.addJob sysUserSessionTimeoutJob + * 2、schedulerManager.triggerJob + * 3、check inf_job_log + */ + } + + @Test + public void testDeleteJob_success() throws SchedulerException { + // mock 数据 + InfJobCreateReqVO createReqVO = randomPojo(InfJobCreateReqVO.class, o -> o.setCronExpression("0 0/1 * * * ? *")); + InfJobDO job = InfJobConvert.INSTANCE.convert(createReqVO); + job.setStatus(InfJobStatusEnum.NORMAL.getStatus()); + fillJobMonitorTimeoutEmpty(job); + jobMapper.insert(job); + schedulerManager.addJob(job.getId(), job.getHandlerName(), job.getHandlerParam(), job.getCronExpression(), + createReqVO.getRetryCount(), createReqVO.getRetryInterval()); + // 调用 UPDATE inf_job SET deleted=1 WHERE id=? AND deleted=0 + jobService.deleteJob(job.getId()); + // 校验数据不存在了 WHERE id=? AND deleted=0 查询为空正常 + assertNull(jobMapper.selectById(job.getId())); + } + + @Test + public void testGetJobListByIds_success() { + // mock 数据 + InfJobDO dbJob = randomPojo(InfJobDO.class, o -> { + o.setStatus(randomEle(InfJobStatusEnum.values()).getStatus()); // 保证 status 的范围 + }); + InfJobDO cloneJob = ObjectUtils.clone(dbJob, o -> o.setHandlerName(randomString())); + jobMapper.insert(dbJob); + // 测试 handlerName 不匹配 + jobMapper.insert(cloneJob); + // 准备参数 + ArrayList ids = new ArrayList<>(); + ids.add(dbJob.getId()); + ids.add(cloneJob.getId()); + // 调用 + List list = jobService.getJobList(ids); + // 断言 + assertEquals(2, list.size()); + assertPojoEquals(dbJob, list.get(0)); + } + + @Test + public void testGetJobPage_success() { + // mock 数据 + InfJobDO dbJob = randomPojo(InfJobDO.class, o -> { + o.setName("定时任务测试"); + o.setHandlerName("handlerName 单元测试"); + o.setStatus(InfJobStatusEnum.INIT.getStatus()); + }); + jobMapper.insert(dbJob); + // 测试 name 不匹配 + jobMapper.insert(ObjectUtils.clone(dbJob, o -> o.setName("土豆"))); + // 测试 status 不匹配 + jobMapper.insert(ObjectUtils.clone(dbJob, o -> o.setStatus(InfJobStatusEnum.NORMAL.getStatus()))); + // 测试 handlerName 不匹配 + jobMapper.insert(ObjectUtils.clone(dbJob, o -> o.setHandlerName(randomString()))); + // 准备参数 + InfJobPageReqVO reqVo = new InfJobPageReqVO(); + reqVo.setName("定时"); + reqVo.setStatus(InfJobStatusEnum.INIT.getStatus()); + reqVo.setHandlerName("单元"); + // 调用 + PageResult pageResult = jobService.getJobPage(reqVo); + // 断言 + assertEquals(1, pageResult.getTotal()); + assertEquals(1, pageResult.getList().size()); + assertPojoEquals(dbJob, pageResult.getList().get(0)); + } + + @Test + public void testGetJobListForExport_success() { + // mock 数据 + InfJobDO dbJob = randomPojo(InfJobDO.class, o -> { + o.setName("定时任务测试"); + o.setHandlerName("handlerName 单元测试"); + o.setStatus(InfJobStatusEnum.INIT.getStatus()); + }); + jobMapper.insert(dbJob); + // 测试 name 不匹配 + jobMapper.insert(ObjectUtils.clone(dbJob, o -> o.setName("土豆"))); + // 测试 status 不匹配 + jobMapper.insert(ObjectUtils.clone(dbJob, o -> o.setStatus(InfJobStatusEnum.NORMAL.getStatus()))); + // 测试 handlerName 不匹配 + jobMapper.insert(ObjectUtils.clone(dbJob, o -> o.setHandlerName(randomString()))); + // 准备参数 + InfJobExportReqVO reqVo = new InfJobExportReqVO(); + reqVo.setName("定时"); + reqVo.setStatus(InfJobStatusEnum.INIT.getStatus()); + reqVo.setHandlerName("单元"); + // 调用 + List list = jobService.getJobList(reqVo); + // 断言 + assertEquals(1, list.size()); + assertPojoEquals(dbJob, list.get(0)); } private static void fillJobMonitorTimeoutEmpty(InfJobDO job) { diff --git a/src/test/resources/sql/clean.sql b/src/test/resources/sql/clean.sql index 329a94064..4345fcb45 100644 --- a/src/test/resources/sql/clean.sql +++ b/src/test/resources/sql/clean.sql @@ -2,6 +2,7 @@ DELETE FROM "inf_config"; DELETE FROM "inf_file"; DELETE FROM "inf_job"; +DELETE FROM "inf_job_log"; -- sys 开头的 DB DELETE FROM "sys_dept"; diff --git a/src/test/resources/sql/create_tables.sql b/src/test/resources/sql/create_tables.sql index 795336435..7dadc2fba 100644 --- a/src/test/resources/sql/create_tables.sql +++ b/src/test/resources/sql/create_tables.sql @@ -29,24 +29,44 @@ CREATE TABLE IF NOT EXISTS "inf_file" ( PRIMARY KEY ("id") ) COMMENT '文件表'; -CREATE TABLE "inf_job" ( - "id" bigint(20) NOT NULL GENERATED BY DEFAULT AS IDENTITY COMMENT '任务编号', - "name" varchar(32) NOT NULL COMMENT '任务名称', - "status" tinyint(4) NOT NULL COMMENT '任务状态', - "handler_name" varchar(64) NOT NULL COMMENT '处理器的名字', - "handler_param" varchar(255) DEFAULT NULL COMMENT '处理器的参数', - "cron_expression" varchar(32) NOT NULL COMMENT 'CRON 表达式', - "retry_count" int(11) NOT NULL DEFAULT '0' COMMENT '重试次数', - "retry_interval" int(11) NOT NULL DEFAULT '0' COMMENT '重试间隔', - "monitor_timeout" int(11) NOT NULL DEFAULT '0' COMMENT '监控超时时间', - "creator" varchar(64) DEFAULT '' COMMENT '创建者', - "create_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间', - "updater" varchar(64) DEFAULT '' COMMENT '更新者', - "update_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间', - "deleted" bit(1) NOT NULL DEFAULT b'0' COMMENT '是否删除', - PRIMARY KEY ("id") +CREATE TABLE IF NOT EXISTS "inf_job" ( + "id" bigint(20) NOT NULL GENERATED BY DEFAULT AS IDENTITY COMMENT '任务编号', + "name" varchar(32) NOT NULL COMMENT '任务名称', + "status" tinyint(4) NOT NULL COMMENT '任务状态', + "handler_name" varchar(64) NOT NULL COMMENT '处理器的名字', + "handler_param" varchar(255) DEFAULT NULL COMMENT '处理器的参数', + "cron_expression" varchar(32) NOT NULL COMMENT 'CRON 表达式', + "retry_count" int(11) NOT NULL DEFAULT '0' COMMENT '重试次数', + "retry_interval" int(11) NOT NULL DEFAULT '0' COMMENT '重试间隔', + "monitor_timeout" int(11) NOT NULL DEFAULT '0' COMMENT '监控超时时间', + "creator" varchar(64) DEFAULT '' COMMENT '创建者', + "create_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间', + "updater" varchar(64) DEFAULT '' COMMENT '更新者', + "update_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间', + "deleted" bit NOT NULL DEFAULT FALSE COMMENT '是否删除', + PRIMARY KEY ("id") ) COMMENT='定时任务表'; +DROP TABLE IF EXISTS "inf_job_log"; +CREATE TABLE "inf_job_log" ( + "id" bigint(20) NOT NULL GENERATED BY DEFAULT AS IDENTITY COMMENT '日志编号', + "job_id" bigint(20) NOT NULL COMMENT '任务编号', + "handler_name" varchar(64) NOT NULL COMMENT '处理器的名字', + "handler_param" varchar(255) DEFAULT NULL COMMENT '处理器的参数', + "execute_index" tinyint(4) NOT NULL DEFAULT '1' COMMENT '第几次执行', + "begin_time" datetime NOT NULL COMMENT '开始执行时间', + "end_time" datetime DEFAULT NULL COMMENT '结束执行时间', + "duration" int(11) DEFAULT NULL COMMENT '执行时长', + "status" tinyint(4) NOT NULL COMMENT '任务状态', + "result" varchar(4000) DEFAULT '' COMMENT '结果数据', + "creator" varchar(64) DEFAULT '' COMMENT '创建者', + "create_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间', + "updater" varchar(64) DEFAULT '' COMMENT '更新者', + "update_time" datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间', + "deleted" bit(1) NOT NULL DEFAULT FALSE COMMENT '是否删除', + PRIMARY KEY ("id") +)COMMENT='定时任务日志表'; + -- sys 开头的 DB CREATE TABLE IF NOT EXISTS "sys_dept" ( From a7a2725a87cea07231cfe7b6239127078553aa05 Mon Sep 17 00:00:00 2001 From: neilz Date: Sun, 14 Mar 2021 21:06:55 +0800 Subject: [PATCH 5/5] =?UTF-8?q?=E5=9B=9E=E9=80=80=E5=A4=9A=E4=BD=99?= =?UTF-8?q?=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../modules/infra/controller/job/vo/job/InfJobBaseVO.java | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/main/java/cn/iocoder/dashboard/modules/infra/controller/job/vo/job/InfJobBaseVO.java b/src/main/java/cn/iocoder/dashboard/modules/infra/controller/job/vo/job/InfJobBaseVO.java index 352c490fc..246f2a7a9 100644 --- a/src/main/java/cn/iocoder/dashboard/modules/infra/controller/job/vo/job/InfJobBaseVO.java +++ b/src/main/java/cn/iocoder/dashboard/modules/infra/controller/job/vo/job/InfJobBaseVO.java @@ -34,7 +34,5 @@ public class InfJobBaseVO { @ApiModelProperty(value = "监控超时时间", example = "1000") private Integer monitorTimeout; - public void setCronExpression(String cronExpression) { - this.cronExpression = cronExpression; - } + }