java EJB 3.x 中@Schedule 方法的动态参数
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/15973661/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Dynamic parameters for @Schedule method in an EJB 3.x
提问by javadev
I'm new to the @Schedule annotations in J2EE6
我是 J2EE6 中 @Schedule 注释的新手
I want to run a job using EJB 3.x with Glassfish 3.1.
我想使用带有 Glassfish 3.1 的 EJB 3.x 运行作业。
The javax.ejb.Schedule seems to be a good choice for us, so we could think of our custom time as something like:
javax.ejb.Schedule 对我们来说似乎是一个不错的选择,所以我们可以把我们的自定义时间看作是这样的:
@Singleton
public class CustomTimer {
@EJB
SettingsFacade settingsFacade;
@Schedule(second="someSecondParameter", minute="someMinuteParameter",hour="someHourParameter", persistent=false)
public void executeTimer(){
//Code executing something against database using the settingsFacade
}
}
Here, we want the parameters to be got from database, so they are changed every month. Any clean solution for this?
在这里,我们希望从数据库中获取参数,因此每个月都会更改它们。任何干净的解决方案?
采纳答案by Mikko Maunu
No, there is no solution with @Schedule
, because annotation attributes in general should be compile time constants.
不,没有解决方案@Schedule
,因为注释属性通常应该是编译时常量。
When more flexibility is needed, programmatic timerscan be used. Also then polling database for changed configuration and removing existing and creating new timers must be implemented.
当需要更大的灵活性时,可以使用编程定时器。此外,还必须实施轮询数据库以更改配置并删除现有计时器和创建新计时器。
回答by Sólon Soares
@Singleton @Startup public class ScheduleTimerService { @Resource private TimerService timerService; public void setTimerService(TimerService timerService) {this.timerService = timerService; } @PostConstruct private void postConstruct() { timerService.createCalendarTimer(createSchedule()); } @Timeout public void timerTimeout(Timer timer) { Add your code here to be called when scheduling is reached... in this example: 01h:30m every day ;-) } private ScheduleExpression createSchedule(){ ScheduleExpression expression = new ScheduleExpression(); expression.dayOfWeek("Sun,Mon,Tue,Wed,Thu,Fri,Sat"); expression.hour("01"); expression.minute("30"); return expression; } }
回答by JavaSun
Well You need to created Two Scheduler One Scheduler will run to update data from Database Based On that You Can created Other Scheduler.
好吧,您需要创建两个调度程序,一个调度程序将运行以更新数据库中的数据,您可以根据它创建其他调度程序。
But for this Need to do it some what programmatic. You also can see EJB Timers for the same what will help you in this case. which is also annotation based.
但是对于这个需要做一些什么程序化的。您还可以查看 EJB 计时器,以了解在这种情况下对您有所帮助的内容。这也是基于注释的。
回答by JoelCarvalho
There is a simple way of doing this. I wanted to something that called a process every day but, the job itself should be done randomly over the same day. I managed to do that by adding a simple thread worker to run after the EJB timer service has been called. Then I would put it to sleep for a random amount of time during that day.
有一种简单的方法可以做到这一点。我想每天做一个过程,但是,工作本身应该在同一天随机完成。我设法通过添加一个简单的线程工作者来实现这一点,以便在调用 EJB 计时器服务之后运行。然后我会让它在那天随机睡眠一段时间。
The following code is an example of a service that wakes up every 1 minute and waits for a thread to finish.
以下代码是每 1 分钟唤醒一次并等待线程完成的服务示例。
@Schedule(minute = "*/1", hour = "*", persistent = false)
public void runEveryMinute() throws InterruptedException {
log.log(Level.INFO, "Scheduling for every minute .. now it's: " + new Date().toString());
// Delay, in milliseconds before we interrupt adding a follower thread
//we can therefore garantee that it runs every day
long patience = 1000 * 5;
threadMessage("Starting forever alone no more thread");
long startTime = System.currentTimeMillis();
Thread t = new Thread(new MessageLoop());
t.start();
threadMessage("Waiting for new thread to finish");
// loop until MessageLoop thread exits
while (t.isAlive()) {
threadMessage("Still waiting...");
// Wait maximum of 1 second for MessageLoop thread to finish.
t.join(1000);
if (((System.currentTimeMillis() - startTime) > patience)
&& t.isAlive()) {
threadMessage("Tired of waiting! Adding new followers now!");
t.interrupt();
// Shouldn't be long now -- wait indefinitely
t.join();
}
}
threadMessage("Finally! You are not alone anymore!");
}
// Display a message, preceded by
// the name of the current thread
static void threadMessage(String message) {
String threadName = Thread.currentThread().getName();
System.out.format("%s: %s%n", threadName, message);
}
private static class MessageLoop implements Runnable {
public void run() {
String importantInfo[] = {
"A kid will eat ivy too"
};
try {
for (int i = 0;
i < importantInfo.length;
i++) {
// Pause for 4 seconds
int max = 10;
int min = 2;
int randomTimer = 0 + (int) (Math.random() * ((max - min) + 1));
Thread.sleep(randomTimer * 1000);
// Print a message
threadMessage(importantInfo[i]);
}
} catch (InterruptedException e) {
threadMessage("Patience is not a virtue! Thread stopping for now!");
}
}
}