Jboss Scheduler sincronizado

Caros,

estou usando o Jboss Scheduler para agendar a execução de um método EJB que deve rodar de 2 em 2 segundos.

A questão é que, se por um acaso, a execução atual não acabar em 2 segundos, a próxima execução não pode começar.

Para evitar isso, eu fiz um controle usando uma variavel estatica como semaforo, porem essa solução não é muito boa, como
todos jah sabem.

Alguem sabe se existe alguma configuração do próprio Jboss Scheduler para fazer isso? Ou senão uma maneira mais elegante
de resolver esse meu problema, e que possa ser escalavel.

Jah procurei na net mas ateh agora não encontrei nada que ajudasse muito.

Obrigado a todos.

[]'s

Olá!

Você está utilizando a interface org.quartz.Job?
Se estiver, você pode utilizar a org.quartz.StatefulJob, que não permite execuções concorrentes.

Pode usar o TimerService da especificação EJB tb.

[]'s

[quote=Rafaelprp]Pode usar o TimerService da especificação EJB tb.

[]'s[/quote]

Eu tentei usar o TimerService, mas não gostei muito.

A primeira coisa que me desagradou é que ele precisa ser iniciado programaticamente.

Daí o que eu fiz foi assinar um método como @PostConstruct e colocar
o start do TimerService lá. Mas daí surge outro problema, que é que o Bean precisa ser instanciado para o @PostConstruct ser chamado, daí
precisei dar um jeito de chamar esse bean uma vez (várias soluções de contorno já).

Porem, o método createTimer() só pode ser chamado uma vez, e como posso ter várias instâncias do meu Bean, usando @PostCosntruct dava errado. Dai a solução que estah ateh no livro “Enterpise Java Beans 3” foi criar um atributo estatico para controlar a criação do createTimer. Mas dai, duas JVMs dá pau de novo, por causa dos estaticos (mais soluções de contorno)

E pra completar, o timerService é persistente. Se o servidor parar e voltar, ele ainda estará lah, ou seja, essa solução de cima mesmo com apenas 1 jvm quebra ai, pois o atributo estatico será reiniciado, dai vai achar que não tem nenhum timerService e vai criar outro, dai pau!! A solução seria cancelar todos os timerServices antes de iniciar um novo, mas dai, eu cansei desse negócio de TimerService e soluções de contorno e desencanei.

No próprio livro "Enterprise Java Beans 3 o autor fala que o timerService é muito ruim. Que seria tão simples se os caras simplesmente tivessem se baseado no cron…mas não…

Acho que vou partir pro Quartz mesmo, porem vou ter que fazer mexidas que não gostaria as vesperas de ir pra produção. Seria tão simples se o Jboss Scheculer tivesse uma tag false.

Obrigado a todos pelas respostas!! E se alguem tiver mais dicas, por favor!! :wink:

Uma forma de fazer o que vc. quer é usar uma combinação do TimerService com um servlet configurado para subir no startup da aplicação.

No método init() do servlet vc. pode chamar um método de “bootstrap” de seu EJB, o qual simplesmente deve obter a referência ao TimerService e fazer um agendamento não recorrente para 2 segundos no futuro.

Ao ser chamado, o método onTimer() deve, após executar a rotina de negócio, se reagendar para 2 segundos no futuro. Desta forma não haverá problema de “encavalamento” de chamadas, e você não ficará amarrado a um recurso específico do JBoss.

Uma recomendação final: se sua rotina de negócio pode levar um tempo significativo (t >= 5s) para executar, tome MUITO cuidado com o gerenciamento de transações feito pelo container. Se o timeout configurado estourar, a transação não será “commitada” ! Desenhe sua rotina desde o início com a possibilidade de se utilizar limitadores (número de registros processados, pex) de forma que o trabalho possa ser executado em blocos