I have a requirement to trigger cron job at 9 am and 10.15 pm every day.
i.e the trigger will be as:
next today at 09:00:00
then today at 22:00:00
then today at 22:15:00
then next day at 09:00:00 and so on...
I have done it as * 0,15 9,22 * * * but it will also get triggered at 9.15 am which I don't want.
Please help me with creating this expression.
If this is not possible can anyone please suggest how to write multiple cron expressions in time triggered azure function. Here is my code:
[FunctionName("Function1")]
public void Run([TimerTrigger("* 0,15 9,22 * * *")] TimerInfo myTimer, ILogger log)
{
//my code here
}
As far as I know, you can't create such a CRON expression in a Function, I can think of what you need to create two functions. A function CRON Expression: * 0 9,22 * *, another CRON expression: * 15 22 * *.
AFAIK you can not create a cron expressions with different distance between each trigger.
You can solve your problem in multiple ways programmatically:
Create a single cron expression that represents the biggest common denominator. E.g.
in your example it would be 15 minutes
so expression would be 0 0/15 0 ? * * *
Make function intelligent enough to decide if it should skip or serve the trigger. E.g. a dumb approach would be:
public class CronFunction {
private void processEvent(String event) {
// process...
}
#FunctionName("cron")
public void cronFunc(
#TimerTrigger(schedule = "0 0 0/1 ? * SAT,SUN *") String event, ExecutionContext context) {
curr_day = ...;
curr_time = ...;
if ((curr_day == today and curr_time in ['09:00:00', '22:00:00', '22:15:00']) ||
(curr_day == tomorrow and curr_time in ['09:00:00'])) {
processEvent(event);
} else {
logger.debug("skipping trigger");
}
}
}
Create multiple triggers, all calling same implementation.
public class CronFunctions {
private void processEvent(String event) {
// process...
}
#FunctionName("cron1")
public void cronFunc1(
#TimerTrigger(schedule = "0 0 0/1 ? * SAT,SUN *") String event, ExecutionContext context) {
processEvent(event);
}
#FunctionName("cron2")
public void cronFunc2(
#TimerTrigger(schedule = "0 0/15 0 ? * MON,TUE,WED,THU,FRI *") String event,
ExecutionContext context) {
processEvent(event);
}
}
Related
I am using a #Scheduled cron job on a method is
Controller A {
#Scheduled(cron = "0 0/2 * * * *", zone = "GMT")
public void methodA() {
// Do something
}`
Is there a way my ControllerB is notified while methodA() is busy?
Controller B {
#Scheduled
public void methodB() {
// I want to be informed that a scheduled job is running
}`
I have a timer-triggered function setup like this
public class PBARCronTrigger
{
private readonly eReserveFunctions _settings;
public PBARCronTrigger(IOptions<eReserveFunctions> settings)
{
_settings = settings.Value;
}
[FunctionName("PBARCronTrigger")]
public async Task Run([TimerTrigger("%PBARCron%")] TimerInfo myTimer, ILogger log)
{
log.LogInformation($"PBARCronTrigger function executing at: {DateTime.Now}");
using (var client = new HttpClient())
and I have the app setting for PBARCron set to every 5 minutes:
but the trigger is not triggering. I connect to live logs and nothing happens. It keeps on saying "No new trace in the past x min(s)"
Your cron expression doesn't look right to me. Checking it in an evaluator even states that it's non-standard and may not work in every environment.
I think what you want is 0-55/5 * * * *, or more simply, */5 * * * *.
I am trying to create a Cron schedule to run at 11:55, 12:00 and 12:05 and using follwing expression-
0 0,5,55 11,12 ? * * *
However above given schedule run at 11:00, 11:05, 11:55, 12:00, 12:05, 12:55. Not sure what I have missed.
You can use 2 triggers to execute YourJob.class.
public class Scheduler extends GenericServlet {
#Override
public void init(ServletConfig config) throws ServletException {
super.init(config);
try {
// this is YOUR job
JobDetail job = JobBuilder.newJob(YourJob.class).build();
Trigger trigger1 = TriggerBuilder
.newTrigger()
.forJob(job)
.withSchedule(
CronScheduleBuilder.cronSchedule(
"0 55 11 ? * * *"
)
).build();
Trigger trigger2 = TriggerBuilder
.newTrigger()
.forJob(job)
.withSchedule(
CronScheduleBuilder.cronSchedule(
"0 0,5 12 ? * * *"
)
).build();
Scheduler scheduler = StdSchedulerFactory.getDefaultScheduler();
scheduler.start();
// run at 11:55 every day
scheduler.scheduleJob(job, trigger1);
// run at 12:00 and 12:05 every day
scheduler.scheduleJob(job, trigger2);
} catch (SchedulerException e) {
Logger.getLogger(Scheduler.class).error(e);
}
}
#Override
public void service(ServletRequest req, ServletResponse res) {
// ...
}
}
I am using Azure Functions with Attributes to define functionality.
public static class PostPublishTimerTrigger
{
[FunctionName("PostPublishTimerTrigger")]
public static void Run([TimerTrigger("0 */5 * * * *")]TimerInfo myTimer,
TraceWriter log,
[Queue("post-published")] ICollector<string> postPublishedQueue)
{
// Additional code here
}
}
Is there a way to pull the Schedule 0 */5 * * * * for a configuration setting, be it with Configuration Manager or Environment Variables?
Thanks!
Yes, you can do
[TimerTrigger("%schedule%")]
and then add a setting called schedule with value 0 */5 * * * *
I have a cron job
<portlet>
<portlet-name>scheduled-actions</portlet-name>
<scheduler-entry>
<scheduler-event-listener-class>com.example.Example</scheduler-event-listener-class>
<trigger>
<cron>
<cron-trigger-value>0/15 * * * * ?</cron-trigger-value>
</cron>
</trigger>
</scheduler-entry>
<system>true</system>
</portlet>
Is it possible to put this cron expression (0/15 * * * * ?) in portal-ext.properties from liferay-portlet.xml? And how to retrive it here if it is?
Thanks
It is possible to add a key in portlet.properties file. We have implemented this.
portlet.properties:
trigger.key=0 0/2 * * * ?
liferay-portlet.xml:
use property-key instead of cron-trigger-value and specify "triger.key"
Agreeing to Matthias answer. Here is what I have done to achieve it,
Extend your scheduler class to MVCPortlet and implement to MessageListener interface.
Now, override init() method by placing the following code,
String cron = "0 0/1 * 1/1 * ? *";// You can read it from portal-ext.properties using PropsUtil
Trigger trigger = null;
try {
trigger = TriggerFactoryUtil.buildTrigger(TriggerType.CRON, EngageMailScheduler.class.getName(), EngageMailScheduler.class.getName(), new Date(), null, cron);
} catch (SchedulerException e) {
e.printStackTrace();
}
Message message = new Message();
message.put(SchedulerEngine.MESSAGE_LISTENER_CLASS_NAME, EngageMailScheduler.class.getName());
message.put(SchedulerEngine.PORTLET_ID, portlet.getPortletId());
try {
//In Liferay 6.1 use SchedulerEngineUtil, it is deprecated in Liferay 6.2
SchedulerEngineHelperUtil.schedule(trigger, StorageType.PERSISTED, "", "liferay/scheduler_dispatch", message, 5);
} catch (SchedulerException e) {
e.printStackTrace();
}
Now, you can place your logic in the receive() method,
public void receive(Message message) throws MessageListenerException {
LOGGER.info("IN: Dynamic scheduler");
}
Finally, give the complete path of your implemented class in liferay-portlet.xml, as below
<portlet-class>com.test.MyScheduler</portlet-class>
Hope this helps.