由于定时任务是用标注实现的,没有XML配置文件,如何设置开关量在不修改代码的情况下控制定时任务的开关呢?
先看下面的例子:
首先定义一个开关配置文件schedule.xml:
<?xml version="1.0" encoding="UTF-8" ?>
<schedule>
<pack name="CommonTask.doSomethingWith" switch="0"></pack>
<pack name="Task.doSomethingWith" switch="0"></pack>
</schedule>
其中name为定时任务的"类名+方法名",switch为开关。
然后建一个初始化类将开关配置读入内存
@Component
public class InitScheduleSwitch {
private static final Log logger = LogFactory
.getLog(InitScheduleSwitch.class);
private static Map<String, String> PACK_SCHEDULE_SWITCH = new HashMap<String, String>();
public static boolean isRun(String name){
String key = PACK_SCHEDULE_SWITCH.get(name);
if(key!=null && key.equals("0")){
return false;
}
return true;
}
@PostConstruct
public void init() {
String path = InitSocketPack.class.getResource("/").getPath()
+ "schedule.xml";
SAXBuilder reader = new SAXBuilder();
try {
Document doc = reader.build(new File(path));
Element root = doc.getRootElement();
List children = root.getChildren();
for (int i = 0, n = children.size(); i < n; i++) {
Element pack = (Element) children.get(i);
String packName = pack.getAttributeValue("name");
String packSchedule = pack.getAttributeValue("switch");
PACK_SCHEDULE_SWITCH.put(packName, packSchedule);
}
} catch (JDOMException e) {
logger.error("read schedule.xml error", e);
} catch (IOException e) {
logger.error("read schedule.xml error", e);
}
}
}
其中isRun(name)方法就是判断定时任务是否开启,参数是约定的”类名+方法名“
再来看看定义定时任务的代码:
@Component
public class CommonTask implements BaseTask {
String className = this.getClass().getSimpleName();
public boolean isRun() {
String method=new Exception().getStackTrace()[1].getMethodName();
if(InitScheduleSwitch.isRun(className+"."+method))
return true;
return false;
}
@Scheduled(cron = "*/1 * * * * *")
void doSomethingWith(){
if(!isRun()) return;
System.out.println("CommonTask $$$");
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
this.getClass().getSimpleName()是取得当前类名,不包含数径。
new Exception().getStackTrace()[1].getMethodName()是取得调用当前方法的方法名,如果下标改成0,则是取得当前方法名。
然后,将取得的"类名+方法名"作为参数传递给先前定义的isRun来判断就行了。