Scheduler定時任務(wù)調(diào)度詳解
更新時間:2025年01月14日 14:52:14 作者:A塵埃
文章介紹了SysJobServiceImpl類中定時任務(wù)調(diào)度的相關(guān)方法,包括清除、檢查存在性、創(chuàng)建、暫停、恢復(fù)、刪除任務(wù),以及觸發(fā)任務(wù),并提到了JobKey、CronUtils、ScheduleUtils、SpringUtils等工具類的使用,適用于Spring管理環(huán)境
Scheduler定時任務(wù)調(diào)度

定時任務(wù)調(diào)度服務(wù)層SysJobServiceImpl
- scheduler.clear();
- scheduler.checkExists(jobKey)
- ScheduleUtils.createScheduleJob(scheduler, job);
- scheduler.pauseJob(ScheduleUtils.getJobKey(jobId, jobGroup));
- scheduler.resumeJob(ScheduleUtils.getJobKey(jobId, jobGroup));
- scheduler.deleteJob(ScheduleUtils.getJobKey(jobId, jobGroup));
- JobKey jobKey = ScheduleUtils.getJobKey(jobId, jobGroup);
- scheduler.triggerJob(jobKey, dataMap);
- CronUtils.isValid(cronExpression)
@Service
public class SysJobServiceImpl implements ISysJobService{
@Autowired
private Scheduler scheduler;//quartz-2.3.2
@Autowired
private SysJobMapper jobMapper;
/**
項目啟動時,初始化定時器
主要是防止手動修改數(shù)據(jù)庫導(dǎo)致未同步到定時任務(wù)處理(注:不能手動修改數(shù)據(jù)庫ID和任務(wù)組名,否則會導(dǎo)致臟數(shù)據(jù))
*/
@PostConstruct
public void init()throws SchedulerException,TaskException{
scheduler.clear();
List<SysJob> jobList = jobMapper.selectJobAll();
for(SysJob job : jobList){
ScheduleUtils.createScheduleJob(scheduler, job);
}
}
/**
獲取quartz調(diào)度器的計劃任務(wù)列表
*/
@Override
public List<SysJob> selectJobList(SysJob job){
return jobMapper.selectJobList(job);
}
/**
* 通過調(diào)度任務(wù)ID查詢調(diào)度信息
*
* @param jobId 調(diào)度任務(wù)ID
* @return 調(diào)度任務(wù)對象信息
*/
@Override
public SysJob selectJobById(Long jobId)
{
return jobMapper.selectJobById(jobId);
}
/**
暫停任務(wù)
*/
@Override
@Transactional(rollbackFor = Exception.class)
public int pause(SysJob job)throws SchedulerException{
Long jobId = job.getJobId();
String jobGroup = job.getJobGroup();
job.setStatus(ScheduleConstants.Status.PAUSE.getValue());
int rows = jobMapper.updateJob(job);
if(rows > 0){
scheduler.pauseJob(ScheduleUtils.getJobKey(jobId,jobGroup));
}
return rows;
}
/**
恢復(fù)任務(wù)
*/
@Override
@Transactional(rollbackFor = Exception.class)
public int resumeJob(SysJob job)throws SchedulerException{
Long jobId = job.getJobId();
String jobGroup = job.getJobGroup();
job.setStatus(ScheduleConstants.Status.NORMAL.getValue());
int rows = jobMapper.updateJob(job);
if(rows > 0){
scheduler.resumeJob(ScheduleUtils.getJobKey(jobId,jobGroup));
}
return rows;
}
/**
刪除任務(wù)后,所對應(yīng)的trigger也將被刪除
*/
@Override
@Transactional(rollbackFor = Exception.class)
public int deleteJob(SysJob job)throws SchedulerException{
Long jobId = job.getJobId();
String jobGroup = job.getJobGroup();
int rows = jobMapper.deleteJobById(jobId);
if(rows > 0){
scheduler.deleteJob(ScheduleUtils.getJobKey(jobId,jobGroup));
}
return rows;
}
/**
批量刪除調(diào)度信息
*/
@Override
@Transactional(rollbackFor = Exception.class)
public void deleteJobByIds(Long[] jobIds)throws SchedulerException{
for(Long jobId:jobIds){
SysJob job = jobMapper.selectJobById(jobId);
deleteJob(job);
}
}
/**
任務(wù)調(diào)度狀態(tài)修改
*/
@Override
@Transactional(rollbackFor = Exception.class)
public int changeStatus(SysJob job)throws SchedulerException{
int rows = 0;
String status = job.getStatus();
if(ScheduleConstants.Status.NORMAL.getValue().equals(status)){
rows = resumeJob(job);
}else if(ScheduleConstants.Status.PAUSE.getValue().equals(status)){
rows = pauseJob(job);
}
return rows;
}
/**
立即運行任務(wù)
*/
@Override
@Transactional(rollbackFor = Exception.class)
public boolean run(SysJob job)throws SchedulerException{
boolean result = false;
Long jobId = job.getJobId();
String jobGroup = job.getJobGroup();
SysJob properties = selectJobById(job.getJobId());
//參數(shù)
JobDataMap dataMap = new JobDataMap();//quartz-2.3.2
dataMap.put(ScheduleConstants.TASK_PROPERTIES,properties);
JobKey jobKey = ScheduleUtils.getJobKey(jobId,jobGroup);
if(scheduler.checkExists(jobkey)){
result = true;
scheduler.triggerJob(jobKey,dataMap);
}
return result;
}
/**
新增任務(wù)
*/
@Override
@Transactional(rollbackFor = Exception.class)
public int insertJob(SysJob job)throws SchedulerException, TaskException{
job.setStatus(ScheduleConstants.Status.PAUSE.getValue());
int rows = jobMapper.insertJob(job);
if(rows > 0){
ScheduleUtils.createScheduleJob(job);
}
return rows;
}
/**
更新任務(wù)的時間表達(dá)式
*/
@Override
@Transactional(rollbackFor = Exception.class)
public int updateJob(SysJob job) throws SchedulerException, TaskException{
SysJob properties = selectJobById(job.getJobId());
int rows = jobMapper.updateJob(job);
if(rows > 0){
updateSchedulerJob(job,properties.getJobGroup());
}
return rows;
}
//更新任務(wù)
public void updateSchedulerJob(SysJob job, String jobGroup) throws SchedulerException, TaskException{
Long jobId = job.getJobId();
//判斷是否存在
JobKey jobKey = ScheduleUtils.getJobKey(jobId,jobGroup);
if(scheduler.checkExists(jobKey)){
// 防止創(chuàng)建時存在數(shù)據(jù)問題 先移除,然后在執(zhí)行創(chuàng)建操作
scheduler.deleteJob(jobKey);
}
ScheduleUtils.createScheduleJob(scheduler, job);
}
//校驗cron表達(dá)式是否有效
@Override
public boolean checkCronExpressionIsValid(String cronExpression){
return CronUtils.isValid(cronExpression)
}
}定時任務(wù)調(diào)度表SysJob
public class SysJob extends BaseEntity{
private static final long serialVersionUID = 1L;
/** 任務(wù)ID */
@Excel(name = "任務(wù)序號", cellType = ColumnType.NUMERIC)
private Long jobId;
/** 任務(wù)名稱 */
@Excel(name = "任務(wù)名稱")
private String jobName;
/** 任務(wù)組名 */
@Excel(name = "任務(wù)組名")
private String jobGroup;
/** 調(diào)用目標(biāo)字符串 */
@Excel(name = "調(diào)用目標(biāo)字符串")
private String invokeTarget;
/** cron執(zhí)行表達(dá)式 */
@Excel(name = "執(zhí)行表達(dá)式 ")
private String cronExpression;
/** cron計劃策略 */
@Excel(name = "計劃策略 ", readConverterExp = "0=默認(rèn),1=立即觸發(fā)執(zhí)行,2=觸發(fā)一次執(zhí)行,3=不觸發(fā)立即執(zhí)行")
private String misfirePolicy = ScheduleConstants.MISFIRE_DEFAULT;
/** 是否并發(fā)執(zhí)行(0允許 1禁止) */
@Excel(name = "并發(fā)執(zhí)行", readConverterExp = "0=允許,1=禁止")
private String concurrent;
/** 任務(wù)狀態(tài)(0正常 1暫停) */
@Excel(name = "任務(wù)狀態(tài)", readConverterExp = "0=正常,1=暫停")
private String status;
public Long getJobId()
{
return jobId;
}
public void setJobId(Long jobId)
{
this.jobId = jobId;
}
@NotBlank(message = "任務(wù)名稱不能為空")
@Size(min = 0, max = 64, message = "任務(wù)名稱不能超過64個字符")
public String getJobName()
{
return jobName;
}
public void setJobName(String jobName)
{
this.jobName = jobName;
}
public String getJobGroup()
{
return jobGroup;
}
public void setJobGroup(String jobGroup)
{
this.jobGroup = jobGroup;
}
@NotBlank(message = "調(diào)用目標(biāo)字符串不能為空")
@Size(min = 0, max = 500, message = "調(diào)用目標(biāo)字符串長度不能超過500個字符")
public String getInvokeTarget()
{
return invokeTarget;
}
public void setInvokeTarget(String invokeTarget)
{
this.invokeTarget = invokeTarget;
}
@NotBlank(message = "Cron執(zhí)行表達(dá)式不能為空")
@Size(min = 0, max = 255, message = "Cron執(zhí)行表達(dá)式不能超過255個字符")
public String getCronExpression()
{
return cronExpression;
}
public void setCronExpression(String cronExpression)
{
this.cronExpression = cronExpression;
}
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
public Date getNextValidTime()
{
if (StringUtils.isNotEmpty(cronExpression))
{
return CronUtils.getNextExecution(cronExpression);
}
return null;
}
public String getMisfirePolicy()
{
return misfirePolicy;
}
public void setMisfirePolicy(String misfirePolicy)
{
this.misfirePolicy = misfirePolicy;
}
public String getConcurrent()
{
return concurrent;
}
public void setConcurrent(String concurrent)
{
this.concurrent = concurrent;
}
public String getStatus()
{
return status;
}
public void setStatus(String status)
{
this.status = status;
}
@Override
public String toString() {
return new ToStringBuilder(this,ToStringStyle.MULTI_LINE_STYLE)
.append("jobId", getJobId())
.append("jobName", getJobName())
.append("jobGroup", getJobGroup())
.append("cronExpression", getCronExpression())
.append("nextValidTime", getNextValidTime())
.append("misfirePolicy", getMisfirePolicy())
.append("concurrent", getConcurrent())
.append("status", getStatus())
.append("createBy", getCreateBy())
.append("createTime", getCreateTime())
.append("updateBy", getUpdateBy())
.append("updateTime", getUpdateTime())
.append("remark", getRemark())
.toString();
}
}/**
* Entity基類
*
* @author ruoyi
*/
public class BaseEntity implements Serializable
{
private static final long serialVersionUID = 1L;
/** 搜索值 */
@JsonIgnore
private String searchValue;
/** 創(chuàng)建者 */
private String createBy;
/** 創(chuàng)建時間 */
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
private Date createTime;
/** 更新者 */
private String updateBy;
/** 更新時間 */
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
private Date updateTime;
/** 備注 */
private String remark;
/** 請求參數(shù) */
@JsonInclude(JsonInclude.Include.NON_EMPTY)
private Map<String, Object> params;
public String getSearchValue()
{
return searchValue;
}
public void setSearchValue(String searchValue)
{
this.searchValue = searchValue;
}
public String getCreateBy()
{
return createBy;
}
public void setCreateBy(String createBy)
{
this.createBy = createBy;
}
public Date getCreateTime()
{
return createTime;
}
public void setCreateTime(Date createTime)
{
this.createTime = createTime;
}
public String getUpdateBy()
{
return updateBy;
}
public void setUpdateBy(String updateBy)
{
this.updateBy = updateBy;
}
public Date getUpdateTime()
{
return updateTime;
}
public void setUpdateTime(Date updateTime)
{
this.updateTime = updateTime;
}
public String getRemark()
{
return remark;
}
public void setRemark(String remark)
{
this.remark = remark;
}
public Map<String, Object> getParams()
{
if (params == null)
{
params = new HashMap<>();
}
return params;
}
public void setParams(Map<String, Object> params)
{
this.params = params;
}
}CronUtils表達(dá)式工具
public class CronUtils{
/**
* 返回一個布爾值代表一個給定的Cron表達(dá)式的有效性
*
* @param cronExpression Cron表達(dá)式
* @return boolean 表達(dá)式是否有效
*/
public static boolean isValid(String cronExpression)
{
return CronExpression.isValidExpression(cronExpression);
}
/**
* 返回一個字符串值,表示該消息無效Cron表達(dá)式給出有效性
*
* @param cronExpression Cron表達(dá)式
* @return String 無效時返回表達(dá)式錯誤描述,如果有效返回null
*/
public static String getInvalidMessage(String cronExpression)
{
try
{
new CronExpression(cronExpression);
return null;
}
catch (ParseException pe)
{
return pe.getMessage();
}
}
/**
* 返回下一個執(zhí)行時間根據(jù)給定的Cron表達(dá)式
*
* @param cronExpression Cron表達(dá)式
* @return Date 下次Cron表達(dá)式執(zhí)行時間
*/
public static Date getNextExecution(String cronExpression)
{
try
{
CronExpression cron = new CronExpression(cronExpression);
return cron.getNextValidTimeAfter(new Date(System.currentTimeMillis()));
}
catch (ParseException e)
{
throw new IllegalArgumentException(e.getMessage());
}
}
}ScheduleUtils定時任務(wù)工具類
public class ScheduleUtils{
/**
* 得到quartz任務(wù)類
*
* @param sysJob 執(zhí)行計劃
* @return 具體執(zhí)行任務(wù)類
*/
private static Class<? extends Job> getQuartzJobClass(SysJob sysJob)
{
boolean isConcurrent = "0".equals(sysJob.getConcurrent());
return isConcurrent ? QuartzJobExecution.class : QuartzDisallowConcurrentExecution.class;
}
/**
* 構(gòu)建任務(wù)觸發(fā)對象
*/
public static TriggerKey getTriggerKey(Long jobId, String jobGroup)
{
return TriggerKey.triggerKey(ScheduleConstants.TASK_CLASS_NAME + jobId, jobGroup);
}
/**
* 構(gòu)建任務(wù)鍵對象
*/
public static JobKey getJobKey(Long jobId, String jobGroup)
{
return JobKey.jobKey(ScheduleConstants.TASK_CLASS_NAME + jobId, jobGroup);
}
/**
* 創(chuàng)建定時任務(wù)
*/
public static void createScheduleJob(Scheduler scheduler, SysJob job) throws SchedulerException, TaskException
{
Class<? extends Job> jobClass = getQuartzJobClass(job);
// 構(gòu)建job信息
Long jobId = job.getJobId();
String jobGroup = job.getJobGroup();
JobDetail jobDetail = JobBuilder.newJob(jobClass).withIdentity(getJobKey(jobId, jobGroup)).build();
// 表達(dá)式調(diào)度構(gòu)建器
CronScheduleBuilder cronScheduleBuilder = CronScheduleBuilder.cronSchedule(job.getCronExpression());
cronScheduleBuilder = handleCronScheduleMisfirePolicy(job, cronScheduleBuilder);
// 按新的cronExpression表達(dá)式構(gòu)建一個新的trigger
CronTrigger trigger = TriggerBuilder.newTrigger().withIdentity(getTriggerKey(jobId, jobGroup))
.withSchedule(cronScheduleBuilder).build();
// 放入?yún)?shù),運行時的方法可以獲取
jobDetail.getJobDataMap().put(ScheduleConstants.TASK_PROPERTIES, job);
// 判斷是否存在
if (scheduler.checkExists(getJobKey(jobId, jobGroup)))
{
// 防止創(chuàng)建時存在數(shù)據(jù)問題 先移除,然后在執(zhí)行創(chuàng)建操作
scheduler.deleteJob(getJobKey(jobId, jobGroup));
}
// 判斷任務(wù)是否過期
if (StringUtils.isNotNull(CronUtils.getNextExecution(job.getCronExpression())))
{
// 執(zhí)行調(diào)度任務(wù)
scheduler.scheduleJob(jobDetail, trigger);
}
// 暫停任務(wù)
if (job.getStatus().equals(ScheduleConstants.Status.PAUSE.getValue()))
{
scheduler.pauseJob(ScheduleUtils.getJobKey(jobId, jobGroup));
}
}
/**
* 設(shè)置定時任務(wù)策略
*/
public static CronScheduleBuilder handleCronScheduleMisfirePolicy(SysJob job, CronScheduleBuilder cb)
throws TaskException
{
switch (job.getMisfirePolicy())
{
case ScheduleConstants.MISFIRE_DEFAULT:
return cb;
case ScheduleConstants.MISFIRE_IGNORE_MISFIRES:
return cb.withMisfireHandlingInstructionIgnoreMisfires();
case ScheduleConstants.MISFIRE_FIRE_AND_PROCEED:
return cb.withMisfireHandlingInstructionFireAndProceed();
case ScheduleConstants.MISFIRE_DO_NOTHING:
return cb.withMisfireHandlingInstructionDoNothing();
default:
throw new TaskException("The task misfire policy '" + job.getMisfirePolicy()
+ "' cannot be used in cron schedule tasks", Code.CONFIG_ERROR);
}
}
/**
* 檢查包名是否為白名單配置
*
* @param invokeTarget 目標(biāo)字符串
* @return 結(jié)果
*/
public static boolean whiteList(String invokeTarget)
{
String packageName = StringUtils.substringBefore(invokeTarget, "(");
int count = StringUtils.countMatches(packageName, ".");
if (count > 1)
{
return StringUtils.containsAnyIgnoreCase(invokeTarget, Constants.JOB_WHITELIST_STR);
}
Object obj = SpringUtils.getBean(StringUtils.split(invokeTarget, ".")[0]);
String beanPackageName = obj.getClass().getPackage().getName();
return StringUtils.containsAnyIgnoreCase(beanPackageName, Constants.JOB_WHITELIST_STR)
&& !StringUtils.containsAnyIgnoreCase(beanPackageName, Constants.JOB_ERROR_STR);
}
}/**
* 定時任務(wù)處理(允許并發(fā)執(zhí)行)
*
* @author ruoyi
*
*/
public class QuartzJobExecution extends AbstractQuartzJob
{
@Override
protected void doExecute(JobExecutionContext context, SysJob sysJob) throws Exception
{
JobInvokeUtil.invokeMethod(sysJob);
}
}/**
* 定時任務(wù)處理(禁止并發(fā)執(zhí)行)
*
* @author ruoyi
*
*/
@DisallowConcurrentExecution
public class QuartzDisallowConcurrentExecution extends AbstractQuartzJob
{
@Override
protected void doExecute(JobExecutionContext context, SysJob sysJob) throws Exception
{
JobInvokeUtil.invokeMethod(sysJob);
}
}/**
* 抽象quartz調(diào)用
*
* @author ruoyi
*/
public abstract class AbstractQuartzJob implements Job
{
private static final Logger log = LoggerFactory.getLogger(AbstractQuartzJob.class);
/**
* 線程本地變量
*/
private static ThreadLocal<Date> threadLocal = new ThreadLocal<>();
@Override
public void execute(JobExecutionContext context) throws JobExecutionException
{
SysJob sysJob = new SysJob();
BeanUtils.copyBeanProp(sysJob, context.getMergedJobDataMap().get(ScheduleConstants.TASK_PROPERTIES));
try
{
before(context, sysJob);
if (sysJob != null)
{
doExecute(context, sysJob);
}
after(context, sysJob, null);
}
catch (Exception e)
{
log.error("任務(wù)執(zhí)行異常 - :", e);
after(context, sysJob, e);
}
}
/**
* 執(zhí)行前
*
* @param context 工作執(zhí)行上下文對象
* @param sysJob 系統(tǒng)計劃任務(wù)
*/
protected void before(JobExecutionContext context, SysJob sysJob)
{
threadLocal.set(new Date());
}
/**
* 執(zhí)行后
*
* @param context 工作執(zhí)行上下文對象
* @param sysJob 系統(tǒng)計劃任務(wù)
*/
protected void after(JobExecutionContext context, SysJob sysJob, Exception e)
{
Date startTime = threadLocal.get();
threadLocal.remove();
final SysJobLog sysJobLog = new SysJobLog();
sysJobLog.setJobName(sysJob.getJobName());
sysJobLog.setJobGroup(sysJob.getJobGroup());
sysJobLog.setInvokeTarget(sysJob.getInvokeTarget());
sysJobLog.setStartTime(startTime);
sysJobLog.setStopTime(new Date());
long runMs = sysJobLog.getStopTime().getTime() - sysJobLog.getStartTime().getTime();
sysJobLog.setJobMessage(sysJobLog.getJobName() + " 總共耗時:" + runMs + "毫秒");
if (e != null)
{
sysJobLog.setStatus("1");
String errorMsg = StringUtils.substring(ExceptionUtil.getExceptionMessage(e), 0, 2000);
sysJobLog.setExceptionInfo(errorMsg);
}
else
{
sysJobLog.setStatus("0");
}
// 寫入數(shù)據(jù)庫當(dāng)中
SpringUtils.getBean(ISysJobLogService.class).addJobLog(sysJobLog);
}
/**
* 執(zhí)行方法,由子類重載
*
* @param context 工作執(zhí)行上下文對象
* @param sysJob 系統(tǒng)計劃任務(wù)
* @throws Exception 執(zhí)行過程中的異常
*/
protected abstract void doExecute(JobExecutionContext context, SysJob sysJob) throws Exception;
}
/**
* 任務(wù)執(zhí)行工具
*
* @author ruoyi
*/
public class JobInvokeUtil
{
/**
* 執(zhí)行方法
*
* @param sysJob 系統(tǒng)任務(wù)
*/
public static void invokeMethod(SysJob sysJob) throws Exception
{
String invokeTarget = sysJob.getInvokeTarget();
String beanName = getBeanName(invokeTarget);
String methodName = getMethodName(invokeTarget);
List<Object[]> methodParams = getMethodParams(invokeTarget);
if (!isValidClassName(beanName))
{
Object bean = SpringUtils.getBean(beanName);
invokeMethod(bean, methodName, methodParams);
}
else
{
Object bean = Class.forName(beanName).getDeclaredConstructor().newInstance();
invokeMethod(bean, methodName, methodParams);
}
}
/**
* 調(diào)用任務(wù)方法
*
* @param bean 目標(biāo)對象
* @param methodName 方法名稱
* @param methodParams 方法參數(shù)
*/
private static void invokeMethod(Object bean, String methodName, List<Object[]> methodParams)
throws NoSuchMethodException, SecurityException, IllegalAccessException, IllegalArgumentException,
InvocationTargetException
{
if (StringUtils.isNotNull(methodParams) && methodParams.size() > 0)
{
Method method = bean.getClass().getMethod(methodName, getMethodParamsType(methodParams));
method.invoke(bean, getMethodParamsValue(methodParams));
}
else
{
Method method = bean.getClass().getMethod(methodName);
method.invoke(bean);
}
}
/**
* 校驗是否為為class包名
*
* @param invokeTarget 名稱
* @return true是 false否
*/
public static boolean isValidClassName(String invokeTarget)
{
return StringUtils.countMatches(invokeTarget, ".") > 1;
}
/**
* 獲取bean名稱
*
* @param invokeTarget 目標(biāo)字符串
* @return bean名稱
*/
public static String getBeanName(String invokeTarget)
{
String beanName = StringUtils.substringBefore(invokeTarget, "(");
return StringUtils.substringBeforeLast(beanName, ".");
}
/**
* 獲取bean方法
*
* @param invokeTarget 目標(biāo)字符串
* @return method方法
*/
public static String getMethodName(String invokeTarget)
{
String methodName = StringUtils.substringBefore(invokeTarget, "(");
return StringUtils.substringAfterLast(methodName, ".");
}
/**
* 獲取method方法參數(shù)相關(guān)列表
*
* @param invokeTarget 目標(biāo)字符串
* @return method方法相關(guān)參數(shù)列表
*/
public static List<Object[]> getMethodParams(String invokeTarget)
{
String methodStr = StringUtils.substringBetween(invokeTarget, "(", ")");
if (StringUtils.isEmpty(methodStr))
{
return null;
}
String[] methodParams = methodStr.split(",(?=([^\"']*[\"'][^\"']*[\"'])*[^\"']*$)");
List<Object[]> classs = new LinkedList<>();
for (int i = 0; i < methodParams.length; i++)
{
String str = StringUtils.trimToEmpty(methodParams[i]);
// String字符串類型,以'或"開頭
if (StringUtils.startsWithAny(str, "'", "\""))
{
classs.add(new Object[] { StringUtils.substring(str, 1, str.length() - 1), String.class });
}
// boolean布爾類型,等于true或者false
else if ("true".equalsIgnoreCase(str) || "false".equalsIgnoreCase(str))
{
classs.add(new Object[] { Boolean.valueOf(str), Boolean.class });
}
// long長整形,以L結(jié)尾
else if (StringUtils.endsWith(str, "L"))
{
classs.add(new Object[] { Long.valueOf(StringUtils.substring(str, 0, str.length() - 1)), Long.class });
}
// double浮點類型,以D結(jié)尾
else if (StringUtils.endsWith(str, "D"))
{
classs.add(new Object[] { Double.valueOf(StringUtils.substring(str, 0, str.length() - 1)), Double.class });
}
// 其他類型歸類為整形
else
{
classs.add(new Object[] { Integer.valueOf(str), Integer.class });
}
}
return classs;
}
/**
* 獲取參數(shù)類型
*
* @param methodParams 參數(shù)相關(guān)列表
* @return 參數(shù)類型列表
*/
public static Class<?>[] getMethodParamsType(List<Object[]> methodParams)
{
Class<?>[] classs = new Class<?>[methodParams.size()];
int index = 0;
for (Object[] os : methodParams)
{
classs[index] = (Class<?>) os[1];
index++;
}
return classs;
}
/**
* 獲取參數(shù)值
*
* @param methodParams 參數(shù)相關(guān)列表
* @return 參數(shù)值列表
*/
public static Object[] getMethodParamsValue(List<Object[]> methodParams)
{
Object[] classs = new Object[methodParams.size()];
int index = 0;
for (Object[] os : methodParams)
{
classs[index] = (Object) os[0];
index++;
}
return classs;
}
}
SpringUtils在非spring管理環(huán)境中獲取bean
/**
* spring工具類 方便在非spring管理環(huán)境中獲取bean
*
* @author ruoyi
*/
@Component
public final class SpringUtils implements BeanFactoryPostProcessor
{
/** Spring應(yīng)用上下文環(huán)境 */
private static ConfigurableListableBeanFactory beanFactory;
@Override
public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException
{
SpringUtils.beanFactory = beanFactory;
}
/**
* 獲取對象
*
* @param name
* @return Object 一個以所給名字注冊的bean的實例
* @throws org.springframework.beans.BeansException
*
*/
@SuppressWarnings("unchecked")
public static <T> T getBean(String name) throws BeansException
{
return (T) beanFactory.getBean(name);
}
/**
* 獲取類型為requiredType的對象
*
* @param clz
* @return
* @throws org.springframework.beans.BeansException
*
*/
public static <T> T getBean(Class<T> clz) throws BeansException
{
T result = (T) beanFactory.getBean(clz);
return result;
}
/**
* 如果BeanFactory包含一個與所給名稱匹配的bean定義,則返回true
*
* @param name
* @return boolean
*/
public static boolean containsBean(String name)
{
return beanFactory.containsBean(name);
}
/**
* 判斷以給定名字注冊的bean定義是一個singleton還是一個prototype。 如果與給定名字相應(yīng)的bean定義沒有被找到,將會拋出一個異常(NoSuchBeanDefinitionException)
*
* @param name
* @return boolean
* @throws org.springframework.beans.factory.NoSuchBeanDefinitionException
*
*/
public static boolean isSingleton(String name) throws NoSuchBeanDefinitionException
{
return beanFactory.isSingleton(name);
}
/**
* @param name
* @return Class 注冊對象的類型
* @throws org.springframework.beans.factory.NoSuchBeanDefinitionException
*
*/
public static Class<?> getType(String name) throws NoSuchBeanDefinitionException
{
return beanFactory.getType(name);
}
/**
* 如果給定的bean名字在bean定義中有別名,則返回這些別名
*
* @param name
* @return
* @throws org.springframework.beans.factory.NoSuchBeanDefinitionException
*
*/
public static String[] getAliases(String name) throws NoSuchBeanDefinitionException
{
return beanFactory.getAliases(name);
}
/**
* 獲取aop代理對象
*
* @param invoker
* @return
*/
@SuppressWarnings("unchecked")
public static <T> T getAopProxy(T invoker)
{
return (T) AopContext.currentProxy();
}
}
Bean工具類
/**
* Bean 工具類
*
* @author ruoyi
*/
public class BeanUtils extends org.springframework.beans.BeanUtils
{
/** Bean方法名中屬性名開始的下標(biāo) */
private static final int BEAN_METHOD_PROP_INDEX = 3;
/** * 匹配getter方法的正則表達(dá)式 */
private static final Pattern GET_PATTERN = Pattern.compile("get(\\p{javaUpperCase}\\w*)");
/** * 匹配setter方法的正則表達(dá)式 */
private static final Pattern SET_PATTERN = Pattern.compile("set(\\p{javaUpperCase}\\w*)");
/**
* Bean屬性復(fù)制工具方法。
*
* @param dest 目標(biāo)對象
* @param src 源對象
*/
public static void copyBeanProp(Object dest, Object src)
{
try
{
copyProperties(src, dest);
}
catch (Exception e)
{
e.printStackTrace();
}
}
/**
* 獲取對象的setter方法。
*
* @param obj 對象
* @return 對象的setter方法列表
*/
public static List<Method> getSetterMethods(Object obj)
{
// setter方法列表
List<Method> setterMethods = new ArrayList<Method>();
// 獲取所有方法
Method[] methods = obj.getClass().getMethods();
// 查找setter方法
for (Method method : methods)
{
Matcher m = SET_PATTERN.matcher(method.getName());
if (m.matches() && (method.getParameterTypes().length == 1))
{
setterMethods.add(method);
}
}
// 返回setter方法列表
return setterMethods;
}
/**
* 獲取對象的getter方法。
*
* @param obj 對象
* @return 對象的getter方法列表
*/
public static List<Method> getGetterMethods(Object obj)
{
// getter方法列表
List<Method> getterMethods = new ArrayList<Method>();
// 獲取所有方法
Method[] methods = obj.getClass().getMethods();
// 查找getter方法
for (Method method : methods)
{
Matcher m = GET_PATTERN.matcher(method.getName());
if (m.matches() && (method.getParameterTypes().length == 0))
{
getterMethods.add(method);
}
}
// 返回getter方法列表
return getterMethods;
}
/**
* 檢查Bean方法名中的屬性名是否相等。<br>
* 如getName()和setName()屬性名一樣,getName()和setAge()屬性名不一樣。
*
* @param m1 方法名1
* @param m2 方法名2
* @return 屬性名一樣返回true,否則返回false
*/
public static boolean isMethodPropEquals(String m1, String m2)
{
return m1.substring(BEAN_METHOD_PROP_INDEX).equals(m2.substring(BEAN_METHOD_PROP_INDEX));
}
}
總結(jié)
以上為個人經(jīng)驗,希望能給大家一個參考,也希望大家多多支持腳本之家。
相關(guān)文章
Java使用建造者模式實現(xiàn)辦理手機(jī)套餐功能詳解
這篇文章主要介紹了Java使用建造者模式實現(xiàn)辦理手機(jī)套餐功能,較為詳細(xì)的描述了建造者模式的概念、原理并結(jié)合實例形式分析了Java使用建造者模式實現(xiàn)的辦理手機(jī)套餐功能具體步驟與相關(guān)操作注意事項,需要的朋友可以參考下2018-05-05
Java中的==和equals()區(qū)別小結(jié)
在Java編程中,理解==操作符和equals()方法的區(qū)別是至關(guān)重要的,本文主要介紹了Java中的==和equals()區(qū)別,具有一定的參考價值,感興趣的可以了解一下2023-08-08
spring security實現(xiàn)下次自動登錄功能過程解析
這篇文章主要介紹了spring security實現(xiàn)記住我下次自動登錄功能,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友可以參考下2019-11-11
Mybatis 實現(xiàn)一個搜索框?qū)Χ鄠€字段進(jìn)行模糊查詢
這篇文章主要介紹了Mybatis 實現(xiàn)一個搜索框?qū)Χ鄠€字段進(jìn)行模糊查詢,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2021-01-01
Springboot使用SPI注冊bean到spring容器的示例代碼
這篇文章主要介紹了Springboot使用SPI注冊bean到spring容器,主要包括mydriver接口,mysqldriver實現(xiàn)過程,本文通過實例代碼給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下2022-10-10

