lunedì 1 settembre 2014

Creare eseguibili schedulati con Quartz

Vai all'indice

L'obiettivo di questo post è creare un'applicazione batch eseguibile schedulata. Per fare questo ho inserito la libreria Quartz nell'esempio descritto nel post precedente, per cui lanciando il processo il risultato dell'elaborazione sarà lo stesso, ma ripetuto ad un intervallo di tempo prestabilito.
Quartz è una libreria open source che permette di schedulare, ovvero pianificare, i processi da una qualsiasi applicazione java. Per fare questo Quartz utilizza la stessa sintassi utilizzata dal crontab di Linux.





Per prima cosa creo un nuovo Java project (File>New>Java project) con Eclipse e definisco un pacchetto prova. Clicco sull'icona di progetto col tasto destro e seleziono Properties dal menù. Mi posiziono sulla scheda Libraries dalla voce Java Build Path ed importo le librerie nel classpath come riportato nella figura.



A questo punto definisco una nuova classe HelloJob.java ed inserisco il codice creato nel post precedente (il test sulle classi String, StringBuilder e StringBuffer).


package prova;

import java.io.File;
import java.io.FileWriter;
import java.io.IOException;

import org.quartz.Job;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;

public class HelloJob implements Job
{
private static StringBuilder oString = new StringBuilder(""); 
public void execute(JobExecutionContext context)
throws JobExecutionException {

   long start=System.currentTimeMillis();
   testString();
   long end=System.currentTimeMillis();
   oString.append("Tempo di esecuzione testString() "+(end-start)+" millis.\n");
   
   start=System.currentTimeMillis();
   testStringBuffer();
   end=System.currentTimeMillis();
   oString.append("Tempo di esecuzione testStringBuffer() "+(end-start)+" millis.\n");
   
   start=System.currentTimeMillis();
   testStringBuilder();
   end=System.currentTimeMillis();
   oString.append("Tempo di esecuzione testStringBuilder() "+(end-start)+" millis.\n");
  
   File file = new File("output.txt");
    try {
    FileWriter fw = new FileWriter(file);
    fw.write(oString.toString());
    fw.flush();
    fw.close();
    } catch (IOException e) {                        
    System.out.println(e);         
    }  
    }  

 private static void testString() {
   String x = "";
   for(int i=0;i<15000;i++){
     //operazione di append
     x+=i;
   }
 }

 private static void testStringBuffer() {
   StringBuffer x = new StringBuffer("");
   for(int i=0;i<15000;i++){
     //operazione di append
     x.append(i);
   }
 }

 private static void testStringBuilder() {
   StringBuilder x = new StringBuilder("");
   for(int i=0;i<15000;i++){
     //operazione di append
     x.append(i);
   }
 }  

}


Definisco la classe Prova.java come entry point. All'interno del metodo main inserisco il codice per l'esecuzione del CronTrigger di Quartz, che tramite un'espressione tipica di Unix ci consente di specificare le date e gli orari in cui eseguire il job.


package prova;

import org.quartz.CronScheduleBuilder;
import org.quartz.Job;
import org.quartz.JobBuilder;
import org.quartz.JobDetail;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.quartz.core.*;
import org.quartz.Scheduler;
import org.quartz.Trigger;
import org.quartz.TriggerBuilder;
import org.quartz.impl.StdSchedulerFactory;

public class Prova  implements Job{

    public static void main( String[] args ) throws Exception
    {
   
    JobDetail job = JobBuilder.newJob(HelloJob.class)
.withIdentity("dummyJobName", "group1").build();

    Trigger trigger = TriggerBuilder
.newTrigger()
.withIdentity("dummyTriggerName", "group1")
.withSchedule(
CronScheduleBuilder.cronSchedule("0/5 * * * * ?"))
.build();

    //schedulo
    Scheduler scheduler = new StdSchedulerFactory().getScheduler();
    scheduler.start();
    scheduler.scheduleJob(job, trigger);

    }

@Override
public void execute(JobExecutionContext arg0) throws JobExecutionException {
// TODO Auto-generated method stub

}
}


In sostanza il codice costruisce un job partendo dalla classe HelloJob e la manda in esecuzione ogni 5 secondi. La riga che determina la pianificazione è:
CronScheduleBuilder.cronSchedule("0/5 * * * * ?"))

Per comprenderla vi consiglio di cercare su Google documentazione sul Crontab di Linux.
Terminata la stesura del codice ho salvato il progetto come Jar eseguibile e creato il file .exe utilizzando Launch4j come descritto nel post precedente.
Lanciando l'eseguibile, il processo ogni 5 secondi accoda nel file output.txt un nuovo report sui tempi di esecuzione delle tre classi String, StringBuffer e StringBuilder.

Nota per chi testasse questo esempio; Una volta lanciata l'esecuzione vi consiglio di terminare il processo javaw tramite  la scheda Processo del pannello di Gestione Attività, in caso contrario il processo continuerà a ciclare fino allo spegnimento del pc.

Hai apprezzato questo post? Conferma le mie competenze o scrivi una segnalazione sul mio profilo Linkedin!