Sunday, June 24, 2012

Quartz 2.0 cron example

This can be considered as an enhancement done to Quartz 2.0 with Spring , which had the job implementations as inner classes. The same can be accomplished with jobs defined as outer classes. The following method schedules the job.

 =======================================================

private void sheduleMyJob() throws SchedulerException, ParseException {

        JobDetail job = newJob(com.shyarmal.quartz.daemon.jobs.MyJob.class)
                .withIdentity("my-job").build();
          
        Map dataMap = job.getJobDataMap();
        dataMap.put("quantity", quantity);
        dataMap.put("myService", myService);
        dataMap.put("unitPrice", unitPrice);

        CronTrigger trigger = newTrigger()
                .withIdentity("my-flag", "priority")
                .withSchedule(cronSchedule(chargeCronExpression)).forJob(job)
                .build();

        scheduler.scheduleJob(job, trigger);

        LOGGER.info("initialized scheduler with expression [{}] \n expression summary([{}]) ",
                trigger.getCronExpression(), trigger.getExpressionSummary());

}

=======================================================

JobDetail and CronTrigger initializations are the same as that in the previous example. Here the parameters to be passed are put to a job data map, which is obtained from JobDetails.
      "  Map dataMap = job.getJobDataMap();
        dataMap.put("quantity", quantity);
        dataMap.put("myService", myService);
        dataMap.put("unitPrice", unitPrice); "
 The scheduler is initialized in the same way as the previous example.

The job class may be of the following form.
=======================================================

package com.shyarmal.quartz.daemon.jobs;

import com.shyarmal.quartz.common.charging.service.IMyService;
import org.quartz.Job;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.List;
import java.util.Map;


public class MyJob implements Job {

    private static final Logger LOGGER = LoggerFactory.getLogger(MyJob.class);

    @Override
    public void execute(JobExecutionContext context) throws JobExecutionException {
        Map dataMap = context.getJobDetail().getJobDataMap();
        int quantity = (Integer) dataMap.get("quantity");
        IMyService myService = (IMyService) dataMap.get("myService");
        double unitPrice = (Double) dataMap.get("unitPrice");
        try {
            // implementation code of your task.
        } catch (Exception e) {
            LOGGER.error("Error occurred while doing job.", e);
        } finally {
            // implementation
        }
    }
}

 =======================================================

JobDetails will be available through the JobExecutionContext passed in to the execute method of the job, from which the job data map can be retrieved. 
       " Map dataMap = context.getJobDetail().getJobDataMap();
        int quantity = (Integer) dataMap.get("quantity");
        IMyService myService = (IMyService) dataMap.get("myService");
        double unitPrice = (Double) dataMap.get("unitPrice"); "



thanks,
Shyarmal.

Web application context (spring load)

Following is an example of how spring beans can be loaded from a servlet. 

The web.xml configuration required is as follows. The spring bean definition xml file path should be given as a context parameter. Spring's ContextLoaderListener has to be defined as a listener in the web.xml. The sub-element 'load-on-startup' should be present in the servlet definition for the servlet to load at the web application is deploy time (If not the servlet will be initialized upon the first request to it).

 ==================================================================
<!DOCTYPE web-app PUBLIC
 "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
 "http://java.sun.com/dtd/web-app_2_3.dtd" >

<web-app>
  <display-name>Archetype Created Web Application</display-name>

    <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>/WEB-INF/spring-beans.xml</param-value>
    </context-param>
    <context-param>
        <param-name>log4jConfigLocation</param-name>
        <param-value>/WEB-INF/log4j.xml</param-value>
        <description>location of log4j configuration file, used by log4jconfiglistener</description>
    </context-param>
    <listener>
        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    </listener>

    <servlet>
        <servlet-name>InitServlet</servlet-name>
        <servlet-class>com.shyarmal.servlet.InitServlet</servlet-class>
        <load-on-startup>1</load-on-startup>
    </servlet>
   
    <servlet-mapping>
        <servlet-name>InitServlet</servlet-name>
        <url-pattern>/init</url-pattern>
    </servlet-mapping>

</web-app>
 ==================================================================

The servlet code is below. The method, init(ServletConfig) [or init()] is overridden to load the web application context with, "WebApplicationContextUtils .getWebApplicationContext(config.getServletContext());". Servlet's init is called when the same is initialized.

 ==================================================================

package com.shyarmal.servlet;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.context.ApplicationContext;
import org.springframework.web.context.support.WebApplicationContextUtils;

import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;



public class InitServlet extends HttpServlet {

    private static final Logger LOGGER = LoggerFactory.getLogger(InitServlet.class);

    @Override
    public void init(ServletConfig config) throws ServletException {
        try {
            LOGGER.debug("initializing email service.");
            ApplicationContext ac = WebApplicationContextUtils              .getWebApplicationContext(config.getServletContext());
            LOGGER.info("Started email service.");
        } catch (Exception e) {
            LOGGER.error("Failed to load application context.", e);
        }
        super.init(config);
    }
}

 ==================================================================


thanks,
Shyarmal.