2012-10-26 12 views
9

Pamiętam, że nie możemy zabić aktualnie działającej Quartz Job, ale możemy przerwać i sprawdzić boolean wszędzie tam, gdzie jest to konieczne, niezależnie od tego, czy będziemy musieli przejść dalej z kolejnymi operacjami, czy nie.Czy można zabić aktualnie działającą pracę kwarcową?

Nawet jeśli implementujemy przerwanie zadania i wywołujemy harmonogram, aby przerwać zadanie, aktualnie uruchomione zadanie będzie nadal działać na serwerze.

Ex:

  1. Nazwany zapytań SQL został wywołany przez zadanie poprzez Hibernate, który trwa długo
  2. Połączenie zostało dokonane na serwerze strony trzeciej, gdzie serwer osoba trzecia trwa długo czas odpowiedzi

http://neopatel.blogspot.in/2011/05/quartz-stop-job.html http://forums.terracotta.org/forums/posts/list/3191.page

Czy ktoś może poprawić moje zrozumienie i wytłumaczyć, w jaki sposób możemy zabić lub zatrzymać "obecnie" wykonywanie pracy?

Dzięki, Kathir

Odpowiedz

2

Jak powiedział, nie ma sposobu, aby przerwać „brutalnie” praca w kwarcu, ani w języku JAVA.

Można hermetyzować logikę zadania w osobnym wątku i uruchomić go za pomocą ExecutorService.

Spójrz na ten przykład: https://stackoverflow.com/a/2275596/1517816

zakładamy QuartzJob jest klasa testowa i przenieść swoją logikę biznesową w klasie zadań.

Nadzieja pomaga

+0

Zgadzam się, że nie możemy brutalnie zabić pracy w Quartz ani w JAVA. Zgadzamy się również, że możemy osiągnąć to samo poprzez ExecutorService. Z mojej ciekawości powstaje jeszcze jedno pytanie, dlaczego Quartz nie wdrożył ExecutorService, aby zapewnić nam sposób na zabicie pracy? A może jest plan na przyszłość w ulepszeniach Kwarcu. Dziękuję za wyjaśnienia i daj mi znać swoje przemyślenia. – Kathir

+0

Dlaczego nie implementuje się prawdopodobnie dlatego, że został zaprojektowany, aby zapewnić alternatywę dla tego braku w jvm. Działa ze starymi jvmsami i jeśli implementują ExecutorService, kwarc zostanie powiązany z ostatnim projektem jvm i force, który zmigruje – poussma

+0

Prawdopodobnie mogą dać dodatkowe lub rozległe wsparcie poprzez konfigurację. W ten sposób mogą osiągnąć zgodność w dół, a także nowe ... czy ja czegoś brakuje? .. W każdym razie dziękuję za poświęcony czas i wyjaśnienie ... – Kathir

6

można utworzyć nową klasę abstrakcyjną nazwie JobBase na przykład, która implementuje interfejs IJob i wstawić metody abstrakcyjne: public abstract void ExecuteJob(IJobExecutionContext context);

Na JobBase można implementuje metodę Execute tak

public abstract class JobBase : IJob,IInterruptableJob 
{ 
    private Thread currentThread; 
    private ILog logger; 
    public JobBase(ILog logger) 
    { 
     this.logger=logger; 
    } 
     public void Execute(IJobExecutionContext context) 
     { 

      var thread = new Thread(()=> 
      { 
       try 
       { 
        this.ExecuteJob(context); 
       } 
       catch(Exception ex) 
       { 
        this.logger.ErrorFormat("Unhandled exception {0}",ex.ToString()); 

       } 
      }); 

      thread.Start(); 
      this.currentThread = thread; 
      this.currentThread.Join(); 
     } 
     public abstract void ExecuteJob(IJobExecutionContext context); 

     public void Interrupt() 
     { 
      currentThread.Abort(); 
     } 
} 

Każda praca będzie wdrażać metodę JobExecute.

public class TestJob :JobBase 
{ 
    private ILog logger; 
    public TeJob(ILog logger):base(logger) 
    { 
    } 

    public override ExecuteJob(IJobExecutionContext context) 
    { 
    } 
} 

zakłada, że ​​stosowanie jakiejś fabryki do tworzenia zadanie

Dla Zatrzymywanie zadania można wywołać metodę scheduler.Interrupt(new JobKey(jobName));

+0

To wygląda dokładnie to, czego potrzebuję. Ale zawsze, gdy próbuję przerwać pracę, otrzymuję wyjątek "ThreadAbortException". – Schoof

+0

@Schoof To jest poprawne. Jeśli przyjrzeć się dokumentacji 'Thread.Abort()' widzisz, że podnosi 'ThreadAbortException' https://msdn.microsoft.com/en-us/library/system.threading.thread.abort(v = vs.110) .aspx –

0

nie wiem dlaczego nikt nie wspomniał o tym, czy może to nie był dostępny w czas, w którym zadano pytanie.

Istnieje metoda o nazwie shutdown dla instancji Scheduler.

SchedulerFactory factory = new StdSchedulerFactor(); 
Scheduler scheduler = factory.getScheduler(); 

Powyższy służy do rozpoczęcia pracy jak

scheduler.start(); 

użytkowania flagę lub coś wiedzieć, kiedy się zatrzymać pracę z systemem.Następnie użyj

scheduler.shutdown(); 

Jak realizowany moje wymagania:

if(flag==true) 
{ 
    scheduler.start(); 
    scheduler.scheduleJob(jobDetail, simpleTrigger); 
} 
else if(flag==false) 
{ 
    scheduler.shutdown(); 
} 

Gdzie jobDetail i simpleTrigger są wymowne.

Mam nadzieję, że to pomaga. :)

+2

To zabije cały harmonogram, zamiast konkretnego zadania w harmonogramie. – Kathir

+2

Tak, tak. Jeśli program planujący ma tylko jedno zadanie. Wtedy ta metoda doskonale by działała. Po prostu podałem sugestię. –

Powiązane problemy