Add Milliseconds to Java Date, When Milliseconds Is Long
I Am Looking for the Best Way to Add Milliseconds to a Java Date When Milliseconds Is Stored as a 'Long'. Java Calendar Has an Add Function, but It Only Takes...
I am looking for the best way to add milliseconds to a Java Date when milliseconds is stored as a 'long'. Java calendar has an add function, but it only takes an 'int' as the amount.
This is one solution I am proposing...
Calendar now = Calendar.getInstance();
Calendar timeout = Calendar.getInstance();
timeout.setTime(token.getCreatedOn());
timeout.setTimeInMillis(timeout.getTimeInMillis() + token.getExpiresIn());
Any other suggestions?
4 Answers
Your solution looks nearly fine to me, actually. I originally posted an answer going via Date, when I hadn't taken getTimeInMillis and setTimeInMillis into account properly.
However, you're calling setTime and then setTimeInMillis which seems somewhat redundant to me. Your code looks equivalent to this:
Calendar timeout = Calendar.getInstance();
timeout.setTimeInMillis(token.getCreatedOn().getTime() + token.getExpiresIn());
A generally nicer alternative would be to use Joda Time though :) It's generally a much nicer date/time API.
You can also create a date with the current local date plus the number of miliseconds you need to add as Expire time
import java.util.Date;
long expiremilis = 60000l; // 1 minute
// Expires in one minute from now
Date expireDate = new Date(System.currentTimeMillis() + expiremilis);
Or the same with a calendar
long expiremilis = 60000l; // 1 minute
Calendar expireDate= Calendar.getInstance();
// Expires on one minute from now
expireDate.setTimeInMillis(System.currentTimeMillis() + expiremilis);
If you use an existing Date object you can do:
import java.util.Date;
long expiremilis = 60000l; // 1 minute
// Expires on one minute from the date object date
Date expireDate = new Date(myDate.getTime() + expiremilis);
And with an existing Calendar Object
long expiremilis = 60000l; // 1 minute
Calendar expireDate= Calendar.getInstance();
// Expires on one minute from the calendar date
expireDate.setTimeInMillis(myCalendar.getTimeInMillis() + expiremilis);
java.time
The java.util Date-Time API and their formatting API, SimpleDateFormat are outdated and error-prone. It is recommended to stop using them completely and switch to the modern Date-Time API*.
Demo using java.time, the modern API:
import java.time.Instant;
public class Main {
public static void main(String[] args) {
Instant createdOn = Instant.ofEpochMilli(1_622_800_000_000L);
System.out.println(createdOn);
Instant timeout = createdOn.plusMillis(50_000L);
System.out.println(timeout);
}
}
See this code run live at IdeOne.com.
Output:
2021-06-04T09:46:40Z
2021-06-04T09:47:30Z
An Instant represents an instantaneous point on the timeline in UTC. The Z in the output is the timezone designator for a zero-timezone offset. It stands for Zulu and specifies the Etc/UTC timezone (which has the timezone offset of +00:00 hours).
So, the solution to your problem would be:
Instant createdOn = token.getCreatedOn().toInstant();
Instant timeout = createdOn.plusMillis(token.getExpiresIn());
Check documentation of Date#toInstant to learn more about it.
Learn more about java.time, the modern Date-Time API* from Trail: Date Time.
* For any reason, if you have to stick to Java 6 or Java 7, you can use ThreeTen-Backport which backports most of the java.time functionality to Java 6 & 7. If you are working for an Android project and your Android API level is still not compliant with Java-8, check Java 8+ APIs available through desugaring and How to use ThreeTenABP in Android Project.
Calendar is a fairly expensive Date object, and it functionality is not the best. If you want an all purpose Date object I suggest looking at JODA Time and it has a function which does what you want.
However, a simpler Java Date object is the Date class as @Dubas indicates.
Even simpler for the type of operation you are performing is to use a long. This is also much faster.
long timeoutMS = token.getCreatedOn() + token.getExpiresIn();
I use long (in GMT) for all my dates and only use Date for the presentation layer. ie. when you want to convert the date to Text.