项目里面要用到定时任务,cron4j满足不了以秒为单位的控制,所以用了quartz,发现个奇怪的问题。
自定义了JFinalJobFactory,用Aop.get()创建quartz的job实例,但发现job实例的@Inject注解在Aop执行doInject时找不到。
public class MyJobFactory implements JobFactory { private final Log log = Log.getLog(MyJobFactory.class); @Override public Job newJob(TriggerFiredBundle bundle, Scheduler scheduler) throws SchedulerException { JobDetail jobDetail = bundle.getJobDetail(); Class jobClass = jobDetail.getJobClass(); try { if (this.log.isDebugEnabled()) { this.log.debug("Producing instance of Job '" + jobDetail.getKey() + "', class=" + jobClass.getName()); } return (Job) Aop.get(jobClass); } catch (Exception var7) { SchedulerException se = new SchedulerException("Problem instantiating class '" + jobDetail.getJobClass().getName() + "'", var7); throw se; } } }
job类,期望是通过Inject注入service
public class xxxQuartz implements InterruptableJob { @Inject private xxxService xxxService; //.... }
debug到这里可以发现,当field是xxxService的时候,inject注解是null的
protected void doInject(Class<?> targetClass, Object targetObject) throws ReflectiveOperationException { targetClass = getUsefulClass(targetClass); Field[] fields = targetClass.getDeclaredFields(); if (fields.length != 0) { for (Field field : fields) { Inject inject = field.getAnnotation(Inject.class); if (inject == null) { continue ; }
Quartz是以在BaseConfig中以Plugin的形式启动的(参考了社区分享里面的QuartzPlugin)
@Override public boolean start() { try { SchedulerFactory sf = new StdSchedulerFactory(schedulerConfig); Scheduler scheduler = sf.getScheduler(); loadJob(jobConfig); scheduler.start(); } catch (SchedulerException | ClassNotFoundException e) { e.printStackTrace(); return false; } return true; }
在这种情况下,不知道为何job类的Inject注解读不到。
但是,在Test方法下启动quartz,却又可以读到Inject注解,并成功注入
@Test public void test() throws ClassNotFoundException { try { String clazz = "xxx"; String config = "xxx"; SchedulerFactory sf = new StdSchedulerFactory(config); Scheduler scheduler = sf.getScheduler(); scheduler.scheduleJob(getJobDetail() , getTrigger()); scheduler.start(); Thread.sleep(60 * 1000l); scheduler.shutdown(); } catch (SchedulerException | InterruptedException e) { e.printStackTrace(); } }
请教一下各位大佬,两种quartz启动方式有何区别,为何一种Inject有效,一种Inject无效
项目:JFinal