5

I am using Quartz Scheduler with my spring 3.0 based application. I am successfully able to create new schedulers and they are working fine.

I have seen thus reference.

But.. I am not able to retrieve servletContext in my quartz job file. can anyone help me for How to retrieve servletContext reference in executeInternal() method ??

Freak
  • 6,786
  • 5
  • 36
  • 54
Gunjan Shah
  • 5,088
  • 16
  • 53
  • 72

3 Answers3

6

I had a similar need. I sorted it out in a similar fashion to the solution presented here. In my servlet context listener I am setting the servlet context using the job data map object which then is set for a job:

    @Override
    public void contextInitialized(ServletContextEvent sce) {
        try {
            //Create & start the scheduler.
            StdSchedulerFactory factory = new StdSchedulerFactory();
            factory.initialize(sce.getServletContext().getResourceAsStream("/WEB-INF/my_quartz.properties"));
            scheduler = factory.getScheduler();
            //pass the servlet context to the job
            JobDataMap jobDataMap = new JobDataMap();
            jobDataMap.put("servletContext", sce.getServletContext());
            // define the job and tie it to our job's class
            JobDetail job = newJob(ImageCheckJob.class).withIdentity("job1", "group1").usingJobData(jobDataMap).build();
            // Trigger the job to run now, and then repeat every 3 seconds
            Trigger trigger = newTrigger().withIdentity("trigger1", "group1").startNow()
                  .withSchedule(simpleSchedule().withIntervalInMilliseconds(3000L).repeatForever()).build();
            // Tell quartz to schedule the job using our trigger
            scheduler.scheduleJob(job, trigger);
            // and start it off
            scheduler.start();
        } catch (SchedulerException ex) {
            log.error(null, ex);
        }
    }

Then inside my job I am doing this:

    @Override
    public void execute(JobExecutionContext context) throws JobExecutionException {
        ServletContext servletContext = (ServletContext) context.getMergedJobDataMap().get("servletContext");
        //...
    }

EDIT: Also since you mention that you are using Spring I found this link, where in the last post a guy mentions to implement ServletContextAware. Personally, I would go with the JobDataMap, since that is its role.

Community
  • 1
  • 1
Boro
  • 7,913
  • 4
  • 43
  • 85
2

Starting from Quartz 2.0, if you are starting the scheduler inside your webapp via QuartzInitializerServlet in your web.xml, you can store ServletContext in your SchedulerContext by setting scheduler-context-servlet-context-key as an init parameter as follows:

<!-- Quartz Scheduler Initializer Servlet -->
<servlet>
    <servlet-name>QuartzInitializer</servlet-name>
    <servlet-class>org.quartz.ee.servlet.QuartzInitializerServlet</servlet-class>
    <init-param>
        <param-name>shutdown-on-unload</param-name>
        <param-value>true</param-value>
    </init-param>
    <init-param>
        <param-name>start-scheduler-on-load</param-name>
        <param-value>true</param-value>
    </init-param>
    <init-param>
        <param-name>scheduler-context-servlet-context-key</param-name>
        <param-value>servletContext</param-value>
    </init-param>
    <load-on-startup>1</load-on-startup>
</servlet>

See the following reference in code: https://github.com/elventear/quartz-scheduler/blob/quartz-2.0.0-rc/quartz/src/main/java/org/quartz/ee/servlet/QuartzInitializerServlet.java#L122

Kalman
  • 8,001
  • 1
  • 27
  • 45
1

To get to your ServletContext from a QuartzJob configure like Kalman said, Then here is some code to get a actual "servletContext"

private void initContext(JobExecutionContext jobContext) {

    Scheduler scheduler = jobContext.getScheduler();
    SchedulerContext schedulerContext = null;
    try {
        schedulerContext = scheduler.getContext();
    } catch (SchedulerException e) {
        e.printStackTrace();
    }

     ServletContext servletContext = (ServletContext)schedulerContext.get("servletContext");
     System.out.println("ServletContextName : "+  servletContext.getServletContextName());