Running timer task at 0200 hrs everyday - java

I have a timer ejb that controls when the application runs that needs to be switched. I need to make it to run at 0200 hrs everyday
public void fireInTwentyFourHours() throws EJBException
TimerService theTimerService = mySessionCtx.getTimerService();
String aLabel = "24 Hours Interval";
//theTimerService.createTimer(new Date(),86400000, aLabel);
String stage = Stage.getStage();
List timerObjects = (List)theTimerService.getTimers();
if(null != timerObjects && timerObjects.size() > 0) {
for(int timerCount=0,size=timerObjects.size();timerCount<size;timerCount++) {
Timer timer = (Timer)timerObjects.get(timerCount);
timer.cancel();
}
}
if(stage.equalsIgnoreCase("P")){
theTimerService.createTimer(getRunTime(),86400000, aLabel);
} else {
theTimerService.createTimer(new Date(),86400000, aLabel);
}
}
private Date getRunTime() {
Calendar gc = new GregorianCalendar();
int year = gc.get(Calendar.YEAR);
int month = gc.get(Calendar.MONTH);
int date = gc.get(Calendar.DAY_OF_MONTH);
Calendar newDate = new GregorianCalendar(year,month,date,17,30,0);
return newDate.getTime();
}
I need to create a new method and make fireInTwentyFourHours to execute at 0200 hrs.
Is this the correct way to make it fire at 0200
public Date getTime(){
Calendar c = Calendar.getInstance();
Date d = c.getTime();
return d;
}
public void fireInTwentyFourHours() throws EJBException
TimerService theTimerService = mySessionCtx.getTimerService();
String aLabel = "24 Hours Interval";
//theTimerService.createTimer(new Date(),86400000, aLabel);
String stage = Stage.getStage();
List timerObjects = (List)theTimerService.getTimers();
if(null != timerObjects && timerObjects.size() > 0) {
for(int timerCount=0,size=timerObjects.size();timerCount<size;timerCount++) {
Timer timer = (Timer)timerObjects.get(timerCount);
timer.cancel();
}
}
if(stage.equalsIgnoreCase("P")){
theTimerService.createIntervalTimer(getTime(),86400000, aLabel);
} else {
theTimerService.createIntervalTimer(new Date(),86400000, aLabel);
}
}
the third parameter is timerConfig how to set that. will it make the code to run at 0200?

Related

A more elegant way to iterate through a list to compare 2 elements next to one another

I have a method which works in this way:
Take as an argument 3 params - a list with dates (sorted in ascending order) , interval unit and interval value
Check whether the next element doesn't exceed the previous date (interval). In other words, given the interval of 30 min, prev - 10:00, next 10:29 - iterate further. if next is 10:31 - break it and return the counter of dates in a row.
The code for it is below:
public static void main(String[] args)
{
Date d1 = new Date();
Date d2 = addOrSubtractTimeUnitFromDate(d1, Calendar.MINUTE, 10, true);
Date d3 = addOrSubtractTimeUnitFromDate(d2, Calendar.MINUTE, 10, true);
Date d4 = addOrSubtractTimeUnitFromDate(d3, Calendar.MINUTE, 10, true);
Date d5 = addOrSubtractTimeUnitFromDate(d4, Calendar.MINUTE, 10, true);
Date d6 = addOrSubtractTimeUnitFromDate(d5, Calendar.MINUTE, 10, true);
List<Date> threeDates = new ArrayList<>();
threeDates.add(d1);
threeDates.add(d2);
threeDates.add(d3);
threeDates.add(d4);
threeDates.add(d5);
threeDates.add(d6);
System.out.println(returnDatesInARowCounter(threeDates, Calendar.MINUTE, 30));
}
private static int returnDatesInARowCounter(List<Date> allDates, int intervalBetween2DatesTimeUnit, int intervalValue)
{
int datesInARowCounter = allDates.size() > 0 ? 1 : 0; // esp. this line (in case allDates is empty)
Date lastDate = null;
Date nextDate;
Iterator<Date> iter = allDates.iterator();
while (iter.hasNext())
{
nextDate = iter.next();
if (lastDate != null) // both lastDate и nextDate are initialized now
{
if(isNextIncidentInIntervalWithLastOneOrNot(lastDate, nextDate, intervalBetween2DatesTimeUnit, intervalValue, true))
{
datesInARowCounter += 1;
}
else break;
}
lastDate = nextDate;
}
return datesInARowCounter;
}
public static Date addOrSubtractTimeUnitFromDate(Date dateToAddToOrSubtractFrom, int calendarTimeUnit, int value, boolean isAdd)
{
if(!isAdd)
{
value = -value;
}
Calendar cal = Calendar.getInstance();
cal.setTime(dateToAddToOrSubtractFrom);
cal.add(calendarTimeUnit, value);
return cal.getTime();
}
private static boolean isNextIncidentInIntervalWithLastOneOrNot(Date lastIncidentRegDate, Date nextIncidentRegDate, int intervalTimeUnit, int intervalValue, boolean isBetween)
{
Date currentIncidentPlusInterval = addOrSubtractTimeUnitFromDate(lastIncidentRegDate, intervalTimeUnit, intervalValue, true);
boolean betweenBool = isDateBetween(nextIncidentRegDate, lastIncidentRegDate, currentIncidentPlusInterval);
return isBetween == betweenBool;
}
private static boolean isDateBetween(Date targetDate, Date startDate, Date endDate)
{
return targetDate.compareTo(startDate) >= 0 && targetDate.compareTo(endDate) <= 0;
}
However, the code looks peculiar to me. Is the any way to make it look more readable?
If you are using Java 8 or newer, you can use the java.time-API instead. It's built-in support for "periods of time" makes the actual implementation much simpler.
static int daysInARow(List<Instant> allInstants, Duration maxDifference) {
int counter = allInstants.size() > 0 ? 1 : 0;
Instant previous = allInstants.get(0);
for (int i = 1; i < allInstants.size(); i++) {
Instant current = allInstants.get(i);
if (Duration.between(previous, current).compareTo(maxDifference) > 0)
break;
counter++;
previous = current;
}
return counter;
}
If you're using java.util.Date in other parts of your project, you can easily convert between Instants by using
Date#from(Instant)
and
Date#toInstant()

Adding days to Date periodically in Java

I want to add days to the current date periodically.
For example, I every 10 seconds that passes, I want to add 1 day to the date today.
08/09/2019 after 10 seconds turns to 08/10/2019...I've already got a working timer, I just dont know how to implement the adding of days part
TimerTask task = new TimerTask() {
#Override
public void run() {
day = day + 1;
model.setDay(day);
Calendar c = Calendar.getInstance();
if(model.getDay() ==1)
c.setTime(date);
Calendar d = Calendar.getInstance();
c.add(Calendar.DAY_OF_MONTH, 1);
d.add(Calendar.DAY_OF_MONTH, 0);
String currentDate = dates2.format(c.getTime());
String currentDate2 = dates2.format(d.getTime());
model.setUpdateDate(currentDate);
model.setUpdateDate2(currentDate2);
}
};
Timer timer = new Timer();
long delay = 10000;
long intervalPeriod = 10000;
You should use java.time types instead of Date and Calendar, which are considered legacy types since Java 8.
Here's an example that may suit you:
public class CountingDays {
private LocalDate date = LocalDate.now();
public static void main(String[] args) {
CountingDays countingDays = new CountingDays();
TimerTask task = new TimerTask() {
#Override
public void run() {
countingDays.date = countingDays.date.plusDays(1);
System.out.println(countingDays.date);
}
};
Timer timer = new Timer();
long delay = 0;
long intervalPeriod = 10_000;
timer.schedule(task, delay, intervalPeriod);
}
}

Android-Week-View loading events per week asynchronously

First off, I'm using the library https://github.com/alamkanak/Android-Week-View
I have an API returning data for one week at a time.
For example GET /stuff/{current_week_number}
Then a scroll listener set up that checks if the week has changed, and will then load
GET /stuff/{new_week_number}
The problem is that all events will be in the current week position as duplicates. I know the library wants events on a per month basis, is it the problem?
Been debugging this for a day now, help would be greatly appreciated.
Function for creating the event:
private WeekViewEvent createNew(JSONObject json, int week) {
String eventTitle = "";
String colorString = "#999";
String startTimeString = "";
String endTimeString = "";
int dayOfWeek = 0;
try {
eventTitle = json.getString("text").replaceAll("\n", " ");
colorString = json.getString("color");
startTimeString = json.getString("startTime");
endTimeString = json.getString("endTime");
dayOfWeek = json.getInt("day");
} catch (JSONException e) {
e.printStackTrace();
}
Calendar startTime = Calendar.getInstance();
startTime.set(Calendar.HOUR_OF_DAY, hoursFromString(startTimeString));
startTime.set(Calendar.MINUTE, minutesFromString(startTimeString));
startTime.set(Calendar.WEEK_OF_YEAR, week);
startTime.set(Calendar.DAY_OF_WEEK, dayOfWeek);
Calendar endTime = (Calendar) startTime.clone();
endTime.set(Calendar.HOUR_OF_DAY, hoursFromString(endTimeString));
endTime.set(Calendar.MINUTE, minutesFromString(endTimeString));
WeekViewEvent event = new WeekViewEvent(mGlobalCounter, eventTitle, startTimeString + " - " + endTimeString, startTime, endTime);
event.setColor(Color.parseColor(colorString));
if (event.getColor() == Color.WHITE) {
event.setColor(R.color.event_color_01);
}
return event;
}
Month change listener + helper method (from example)
private boolean eventMatches(WeekViewEvent event, int year, int month) {
return (event.getStartTime().get(Calendar.YEAR) == year && event.getStartTime().get(Calendar.MONTH) == month - 1) || (event.getEndTime().get(Calendar.YEAR) == year && event.getEndTime().get(Calendar.MONTH) == month - 1);
}
MonthLoader.MonthChangeListener mMonthChangeListener = new MonthLoader.MonthChangeListener() {
#Override
public List<WeekViewEvent> onMonthChange(int newYear, int newMonth) {
// Populate the week view with some events.
List<WeekViewEvent> events = new ArrayList<>(); //getEvents(newYear, newMonth);
for (WeekViewEvent event : mNewEvents) {
if (eventMatches(event, newYear, newMonth)) {
events.add(event);
}
}
mFetchedWeeks.add(Integer.valueOf(mWeek));
return events;
}
};
And here's the JSON-response from the API
https://gist.github.com/jonathanort/668de267966e3b673fffe23dfbdfb90b
Also, my modified version of WeekView.java
https://gist.github.com/jonathanort/472d86355dcdbc338f13373a838f548a
The solution was to add the line
startTime.get(Calendar.DAY_OF_WEEK);
before
startTime.set(Calendar.DAY_OF_WEEK, dayOfWeek);
Apparently it will not set the day otherwise

Why my Java alarm clock code doesn't work properly?

I want the code to trigger the JOptionPane.
Here is the code for the working clock:
new Thread() {
public void run() {
while (true) {
GregorianCalendar cal = new GregorianCalendar();
int hour = cal.get(GregorianCalendar.HOUR);
int min = cal.get(GregorianCalendar.MINUTE);
int sec = cal.get(GregorianCalendar.SECOND);
int AM_PM = cal.get(GregorianCalendar.AM_PM);
String day_night;
if (AM_PM == 1) {
day_night = "PM";
} else {
day_night = "AM";
}
String time = hour + ":" + min + ":" + sec + " " + day_night;
lblClock.setText(time);
}
}
}.start();
Here is code I wrote to trigger alarm, but no 'play sound' is coded yet, because I can't even get the JOptionPane to appear. Why? I want to get the values from spinners, than compare to real time until they meet and than trigger alarm and exit thread. How to fix it?
btnAlarm.addMouseListener(new MouseAdapter() {
#Override
public void mouseClicked(MouseEvent arg0) {
new Thread() {
public void run() {
txtAlarmSet.setVisible(true);
boolean flag = false;
GregorianCalendar g = new GregorianCalendar();
int hour = Integer.parseInt(spinnerHour.getModel().getValue().toString());
int minute = Integer.parseInt(spinnerMinute.getModel().getValue().toString());
int second = Integer.parseInt(spinnerSecond.getModel().getValue().toString());
int AMorPM;
if (rdbtnAm.isSelected()) {
AMorPM = 0;
} else
AMorPM = 1;
while (flag == false) {
int realHour = g.get(GregorianCalendar.HOUR);
int realMinute = g.get(GregorianCalendar.MINUTE);
int realSecond = g.get(GregorianCalendar.SECOND);
int realAM_PM = g.get(GregorianCalendar.AM_PM);
if (hour == realHour && minute == realMinute && second == realSecond
&& AMorPM == realAM_PM) {
JOptionPane.showMessageDialog(null, "WORKS!"); // <- this doesn't appear!
flag = true;
}
}
txtAlarmSet.setVisible(false);
}
}.start();
}
});
In your checking loop, you need to reacquire the Calendar on every pass, otherwise, you'll just end up re-checking the same time value over and over. Move the line
GregorianCalendar g = new GregorianCalendar();
inside the loop.
Note: This is not a particularly good approach to this problem. What you're doing is called "busy waiting" and it's generally not good for much other than making the CPU get hot. A better approach would be to use an event-driven approach, but that's beyond the scope of this answer.
One major problem I notice is missing } after AMorPM = 1; making it impossible to work for AM.

JSpinner time constraint

I am trying to create a spinner that has hours and minutes. The minutes part needs to increment by 10 mins only and the time must range from the current time to an end time. I also need the minimum value (previously current time) to update to current time.
I tried playing around with it, but I just couldn't get it to work.
JSpinner spinner1 = new javax.swing.JSpinner();
SpinnerDateModel spinnermodel = new SpinnerDateModel();
spinnermodel.setCalendarField(Calendar.MINUTE);
spinner1.setModel(spinnermodel);
spinner1.setEditor(new JSpinner.DateEditor(spinner1, "hh:mm"));
SpinnerModel model = new SpinnerDateModel(currentDate, currentDate, latestDate, Calendar.MINUTE * 10 ?);
The SpinnerDateModel just uses 1 to increment the field you want to change.
I extended the SpinnerDateModel to add an addition property to the model to control the increment value instead of hard coding to 1:
import java.util.*;
import javax.swing.*;
public class MySpinnerDateModel extends SpinnerDateModel
{
private int increment = 1;
public MySpinnerDateModel(Date value, Comparable start, Comparable end, int calendarField)
{
super(value, start, end, calendarField);
}
public MySpinnerDateModel()
{
this(new Date(), null, null, Calendar.DAY_OF_MONTH);
}
public void setIncrement(int increment)
{
this.increment = increment;
}
public int getIncrement()
{
return increment;
}
#Override
public Object getNextValue()
{
Calendar cal = Calendar.getInstance();
Date value = (Date)getValue();
cal.setTime(value);
cal.add(getCalendarField(), increment);
Date next = cal.getTime();
Comparable end = getEnd();
return ((end == null) || (end.compareTo(next) >= 0)) ? next : null;
}
#Override
public Object getPreviousValue()
{
Calendar cal = Calendar.getInstance();
Date value = (Date)getValue();
cal.setTime(value);
cal.add(getCalendarField(), -increment);
Date prev = cal.getTime();
Comparable start = getStart();
return ((start == null) || (start.compareTo(prev) <= 0)) ? prev : null;
}
}
You should be able to use the model the way you did before but with one additional statement:
MySpinnerDateModel model = new MySpinnerDateModel(currentDate, currentDate, latestDate, Calendar.MINUTE);
model.setIncrement( 10 );
You can extend the SpinnerDateModel to specify the behavior. Below is an example in which the getNextValue and getPreviousValue are overridden to return values +/- 10 minutes:
Date now = new Date();
Date start = now;
final long tenMinutesInMillis = 1000 * 60 * 10;
Date end = new Date(now.getTime() + tenMinutesInMillis * 60);
SpinnerModel model = new SpinnerDateModel(now, start, end, Calendar.MINUTE){
#Override
public Object getNextValue(){
Date newDate = new Date(getDate().getTime() + tenMinutesInMillis);
Date endDate = (Date)getEnd();
return newDate.getTime() > endDate.getTime() ? endDate : newDate;
}
#Override
public Object getPreviousValue(){
Date newDate = new Date(getDate().getTime() - tenMinutesInMillis);
Date startDate = (Date)getStart();
return newDate.getTime() < startDate.getTime() ? startDate : newDate;
}
};

Categories