I want to get the current time in UTC. What I do so far is following (just for testing purposes):
DateTime dt = new DateTime();
DateTimeZone tz = DateTimeZone.getDefault();
LocalDateTime nowLocal = new LocalDateTime();
DateTime nowUTC = nowLocal.toDateTime(DateTimeZone.UTC);
Date d1 = nowLocal.toDate();
Date d2 = nowUTC.toDate();
L.d("tz: " + tz.toString());
L.d("local: " + d1.toString());
L.d("utc: " + d2.toString());
d1 is my local time, that's fine
d2 is my local time + 1, but should be local time - 1...
My local time zone is UTC+1 (according to the debug output and the list here: https://www.joda.org/joda-time/timezones.html)...
How do I correctly convert from one time zone to another (inclusive the millisecond representation)?
EDIT
I need the date/milliseconds... It's NOT about displaying the time correctly....
EDIT 2
Now, with the help of a comment and an answer, I tried following:
DateTimeZone tz = DateTimeZone.getDefault();
DateTime nowLocal = new DateTime();
LocalDateTime nowUTC = nowLocal.withZone(DateTimeZone.UTC).toLocalDateTime();
DateTime nowUTC2 = nowLocal.withZone(DateTimeZone.UTC);
Date dLocal = nowLocal.toDate();
Date dUTC = nowUTC.toDate();
Date dUTC2 = nowUTC2.toDate();
L.d(Temp.class, "------------------------");
L.d(Temp.class, "tz : " + tz.toString());
L.d(Temp.class, "local : " + nowLocal + " | " + dLocal.toString());
L.d(Temp.class, "utc : " + nowUTC + " | " + dUTC.toString()); // <= WORKING SOLUTION
L.d(Temp.class, "utc2 : " + nowUTC2 + " | " + dUTC2.toString());
OUTPUT
tz : Europe/Belgrade
local : 2015-01-02T15:31:38.241+01:00 | Fri Jan 02 15:31:38 MEZ 2015
utc : 2015-01-02T14:31:38.241 | Fri Jan 02 14:31:38 MEZ 2015
utc2 : 2015-01-02T14:31:38.241Z | Fri Jan 02 15:31:38 MEZ 2015
What I wanted was, that the local date displays 15 o'clock and utc date displays 14 o'clock...
For now, this seems to work...
----- EDIT3 - Final solution -----
Hopefully, this is a good solution... I think, i respects all tipps i got...
DateTimeZone tz = DateTimeZone.getDefault();
DateTime nowUTC = new DateTime(DateTimeZone.UTC);
DateTime nowLocal = nowUTC.withZone(tz);
// This will generate DIFFERENT Dates!!! As I want it!
Date dLocal = nowLocal.toLocalDateTime().toDate();
Date dUTC = nowUTC.toLocalDateTime().toDate();
L.d("tz : " + tz.toString());
L.d("local : " + nowLocal + " | " + dLocal.toString());
L.d("utc : " + nowUTC + " | " + dUTC.toString());
Output:
tz : Europe/Belgrade
local : 2015-01-03T21:15:35.170+01:00 | Sat Jan 03 21:15:35 MEZ 2015
utc : 2015-01-03T20:15:35.170Z | Sat Jan 03 20:15:35 MEZ 2015
You're making it far more complicated than you need to:
DateTime dt = new DateTime(DateTimeZone.UTC);
No conversion required at all. If you find you actually need to convert, you can use withZone. I'd suggest you avoid going via LocalDateTime, however, as that way you can lose information due to time zone transitions (two different instants can have the same local time in the same time zone, because clocks go back and repeat local time.
Having said all of this, for the sake of testability I personally like using a Clock interface which allows me to get the current time (e.g. as an Instant). You can then use dependency injection to inject a real system clock when running in production, and a fake clock with a preset time for tests. Java 8's java.time package has this idea built into it, btw.
You can also use the static method now which makes it even more readable
DateTime.now(DateTimeZone.UTC)
Use this
DateTime.now().withZone(DateTimeZone.UTC)
and if you want to format, you can use
DateTime.now().withZone(DateTimeZone.UTC).toString("yyyyMMddHHmmss")
Please try to listen to Jon Skeets good advise and comments. Here an additional explanation. Your edit-2 contains a mistake:
DateTimeZone tz = DateTimeZone.getDefault();
DateTime nowLocal = new DateTime();
LocalDateTime nowUTC = nowLocal.withZone(DateTimeZone.UTC).toLocalDateTime();
DateTime nowUTC2 = nowLocal.withZone(DateTimeZone.UTC);
Date dLocal = nowLocal.toDate();
Date dUTC = nowUTC.toDate();
Date dUTC2 = nowUTC2.toDate();
If you call toDate() on an object nowUTC of type LocalDateTime then you can get surprises - see javadoc. Joda-Time claims to use the same fields in java.util.Date as in nowUTC. What does this mean? Let's analyze:
nowUTC.toString() produces 2015-01-02T14:31:38.241 That is without timezone (note the missing Z at the end), so it is just a plain local timestamp. By context, we know it was generated in UTC. In your next step however, you convert it to a java.util.Date using the mentioned method above. This method combines the local timestamp with the system timezone (Belgrade) PRESERVING the FIELDS, hence CHANGING the instant. So you have finally miscorrected your instant. And your second line is wrong.
If you just want
utc date displays 14 o'clock
then don't use the questionable and misleading conversion method Joda-Time offers. Use instead a dedicated formatter with the pattern "EEE MMM dd HH:mm:ss zzz yyyy" or similar (Joda-Time offers DateTimeFormatter). Set the UTC-offset on this formatter and print. Done. Abandon completely any call of java.util.Date.toString(). This way, you don't even need to do any dangerous conversion at all.
From here: http://www.joda.org/joda-time/userguide.html#Changing_TimeZone
// get current moment in default time zone
DateTime dt = new DateTime();
// translate to London local time
DateTime dtLondon = dt.withZone(DateTimeZone.forID("Europe/London"));
The resulting value dtLondon has the same absolute millisecond time, but a different set of field values.
You can substitute `Europe/London' for the timezone you want (UTC). See this list of proper time zone names.
SimpleDateFormat sdf = new SimpleDateFormat( "yyyy-MM-dd HH:mm:ss" );
// or SimpleDateFormat sdf = new SimpleDateFormat( "MM/dd/yyyy KK:mm:ss a Z" );
sdf.setTimeZone( TimeZone.getTimeZone( "UTC" ) );
System.out.println( sdf.format( new Date() )
);
Instead of System.out.println( sdf.format( new Date() ) put your local date
I fixed this with this converter
public class DateTimeConverter implements AttributeConverter<DateTime, Date> {
#Override
public Date convertToDatabaseColumn(DateTime attribute) {
return attribute == null ? null
: new Date(attribute
.withZone(DateTimeZone.UTC)
.withZoneRetainFields(DateTimeZone.getDefault())
.getMillis());
}
#Override
public DateTime convertToEntityAttribute(Date dbData) {
return dbData == null ? null
: new DateTime(dbData.getTime())
.withZoneRetainFields(DateTimeZone.UTC)
.withZone(DateTimeZone.getDefault());
}
}
Dates are stored as UTC and recovered with your current time zone
Related
I want to get the time in UTC time zone. So I wrote the code:
import java.time.ZoneOffset;
import java.time.ZonedDateTime;
import java.util.Date;
public class RegularSandbox {
public static void main(String[] args) {
ZonedDateTime utc = ZonedDateTime.now(ZoneOffset.UTC);
System.out.println("DATETIME = " + Date.from(utc.toInstant()));
}
}
The problem is the output shows me the time in PST (my local timezone). I need it to output the time in UTC so I can store it inside of my databases.
System.out.println("DATETIME = " + utc.format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
You do too much when trying to convert to old java.util.Date. And then you implicitly use its method toString() which should be well known for the observed behaviour to print the instant always in your system timezone.
But printing in UTC timezone is extremely simple, not even a formatter is needed if you can cope with ISO-8601-notation:
ZonedDateTime utc = ZonedDateTime.now(ZoneOffset.UTC);
System.out.println("DATETIME = " + utc.toInstant());
// output: DATETIME = 2015-12-30T15:01:18.483Z (Instant is always printed with UTC offset)
System.out.println("DATETIME = " + utc);
// output: DATETIME = 2015-12-30T15:01:57.611Z (the same because you
// have explicitly set the UTC Offset when constructing the ZonedDateTime)
You see, the behaviour of toString() of the new Java-8 classes Instant and ZonedDateTime is much clearer and is always in ISO-format. No need for a confusing conversion to Date.
About specialized formatters, you will only need one if you intend to deviate from ISO-8601-format - maybe using localized month names or extra printing of weekdays etc. Example in US-style:
System.out.println(
"DATETIME = "
+ utc.format(DateTimeFormatter.ofPattern("MM/dd/uuuu h:mm:ss a xxx")));
// output: DATETIME = 12/30/2015 3:14:50 PM +00:00
Note that the answer of #LowLevel uses a wrong pattern. If you leave out the symbol a (AM/PM-marker) then you should not choose the half-day-hour-symbol h but H (24-hour-format). And the timezone or offset symbol (here x) is crucial because otherwise the printed datetime will not be automatically recognized as being in UTC timezone.
ZonedDateTime utc = ZonedDateTime.now(ZoneOffset.UTC);
final SimpleDateFormat sdf = new SimpleDateFormat("EEE, MMM d, yyyy hh:mm:ss a z"); // you can specify format that you want to get
sdf.setTimeZone(TimeZone.getTimeZone("UTC"));
System.out.println("UTC time: " + sdf.format(utc));
private Calendar getUTCTime(){
Calendar calendar = Calendar.getInstance();
// Assuming your time is in utc + 8
calendar.add(Calendar.HOUR, -8);
return calendar;
}
I suggest you to use Joda-Time.
DateTime dt = new DateTime(DateTimeZone.UTC);
I have a football match date and time as UK time.
I am running this service in South Africa so it must display the fixture date and time as South African time. At the moment I am doing this:
int kickoffHour = fixture.getTime().getHours() + 2;
However - when it reaches end of March 2016 this will have to change again to "+ 1" instead of "+ 2". Now I can't keep changing this so I want something that will automatically pick up that its DST or BST and do the conversion.
I have tried something like this:
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
sdf.setTimeZone(TimeZone.getTimeZone("Europe/London"));
Date date = sdf.parse(fixture.getDate() + " " + fixture.getTime());
But that gave me like 2am or something. My date in the database is: 2015-12-16 and the time in the database is 16:00:00 - after parsing I get Wed Dec 16 02:00:00 SAST 2015
Apparently you are referring to adjustments needed for Daylight Saving Time (DST). You should leave such work to a good date-time library rather than manage these details yourself.
Unfortunately, the old date-time classes bundled with early versions of Java are not good. While a valiant effort, they have proven to be troublesome and confusing, flawed in both design and implementation. Avoid java.util.Date/.Calendar and java.text.SimpleDateFormat.
java.time
The java.time framework built into Java 8 and later supplants the troublesome old java.util.Date/.Calendar classes. The new classes are inspired by the highly successful Joda-Time framework, intended as its successor, similar in concept but re-architected. Defined by JSR 310. Extended by the ThreeTen-Extra project. See the Tutorial.
By the way, best practice is to do all your business logic, data storage & exchange, and database work in UTC. Use zoned date-time values only when expected by the user or data sink. However, it appears you have been given a string in London time, so let's go with that.
String input = "2015-12-16 16:00:00"; // Local date-time in United Kingdom (London).
Use proper time zone names. Never use the 3-4 letter codes commonly seen as they are neither standardized nor unique.
DateTimeFormatter formatter = DateTimeFormatter.ofPattern ( "yyyy-MM-dd HH:mm:ss" );
Your string input lacks embedded info about its offset-from-UTC or time zone. So, we will assume the String represents local time in Europe/London. We communicate this assumption to the DateTimeFormatter, as it would otherwise interpret the incoming String as belonging to the JVM’s current default time zone. Note that java.time uses immutable objects, so rather than alter the formatter we generate a new instance based on values take from the old instance.
ZoneId zoneId_London = ZoneId.of ( "Europe/London" );
formatter = formatter.withZone ( zoneId_London ); // Specify the zone by which to interpret this date-time input string as it lacks any offset or time zone info.
ZonedDateTime zdt_UK = ZonedDateTime.parse ( input , formatter );
With a London date-time in hand, we can adjust into a South Africa time zone.
ZoneId zoneId_Johannesburg = ZoneId.of ( "Africa/Johannesburg" );
ZonedDateTime zdt_ZA = zdt_UK.withZoneSameInstant ( zoneId_Johannesburg );
Dump to console.
System.out.println ( "input: " + input + " in zone: " + zoneId_London + " = " + zdt_UK );
System.out.println ( "zdt_UK: " + zdt_UK + " adjusted to zone: " + zoneId_Johannesburg + " is: " + zdt_ZA );
input: 2015-12-16 16:00:00 in zone: Europe/London = 2015-12-16T16:00Z[Europe/London]
zdt_UK: 2015-12-16T16:00Z[Europe/London] adjusted to zone: Africa/Johannesburg is: 2015-12-16T18:00+02:00[Africa/Johannesburg]
Lastly, we do most of our work in UTC. For that, extract a Instant object which is a moment on the timeline in UTC.
Instant instant = zdt_ZA.toInstant();
if fixture.getDate() + " " + fixture.getTime() works fine, at the end you will get the String as "2015-12-16 16:00:00".
Then I simply format the returning date. Mine works fine..
public static void main(String[] args) throws ParseException {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
sdf.setTimeZone(TimeZone.getTimeZone("Europe/London"));
Date date = sdf.parse("2015-12-16 16:00:00");
//Date date = sdf.parse("2016-03-31 23:50:50");
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
df.setTimeZone(TimeZone.getTimeZone("Africa/Johannesburg"));
System.out.println(df.format(date));
}
Output of this code is 2015-12-16 18:00:00
When I use commented date object, result was 2016-04-01 00:50:50
You can simply get the time values from the fixture and use calendar to auto convert your time zone. I am keeping in mind that your system timezone matches the expected output timezone. Please check the below code snipet, w/o using fixture object and using hard coded value.
Calendar cal = Calendar.getInstance();
cal.setTimeZone(java.util.TimeZone.getTimeZone("Europe/London"));
cal.set(Calendar.HOUR, 16);
cal.set(Calendar.MINUTE, 0);
cal.set(2015, 11, 24);
System.out.println(cal.getTimeZone());
System.out.println(cal.getTime()); //printing in IST (my local time)
You should have a Date object from your database.
If you want to print it, use your SimpleDateFormat setting its timezone to South Africa "Africa/Johannesburg" and it will work.
Date myDate;
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
sdf.setTimeZone(TimeZone.getTimeZone("Africa/Johannesburg"));
System.out.println(sdf.format(myDate));
guys.
im newbie in using joda time api. so here is my question. Ive app server deploy somewhere in the western region and the date fixed to the particular time , Fri Feb 6 08:50:54 UTC 2015.
however, i try to use joda time zone to change the timezone to my country. it didnt worked out. i have run out of ideas. below is my code :
java.util.Date dateIn = new java.util.Date();
DateTime dateTimeUtc = new DateTime( dateIn, DateTimeZone.UTC );
System.out.println("date time utc : " + dateTimeUtc);
DateTimeZone timeZoneLos_Angeles = DateTimeZone.forID( "America/Los_Angeles" ); // Adjust time zone to United States.
DateTime dateTimeLos_Angeles = dateTimeUtc.withZone( timeZoneLos_Angeles );
System.out.println("los angeles date time : " + dateTimeLos_Angeles.toDate());
DateTimeZone timeZoneMalaysia = DateTimeZone.forID( "Asia/Singapore" );
DateTime dateTimeKL = dateTimeLos_Angeles.withZone( timeZoneMalaysia );
System.out.println("KL date time : " + dateTimeKL.toDate());
java.util.Date newDate = dateTimeKL.toDate();
System.out.println("after convert to j.u.Date : " + newDate);
the output:
date time utc : 2015-02-06T08:58:29.127Z
los angeles date time : Fri Feb 06 16:58:29 SGT 2015
KL date time : Fri Feb 06 16:58:29 SGT 2015
after convert to j.u.Date : Fri Feb 06 16:58:29 SGT 2015
i dont know what's going on now. joda time is using my local machine time.
can u guys explain what is happening here? am i accessing joda time in wrong way. or is it my mistake?
A java.util.Date is basically the same thing as a joda-time Instant: an instant on the universal time scale. It doesn't have any time zone. It's just a number of milliseconds wrapped into an object. So when you call toString() on a java.util.Date instance, this object tries to make this number of millisecond readable to you, and transforms it to a readable date using the default timezone of the JVM: SGT in this case.
If you want to see a date in a given timezone, then print the DateTime instance itself (which contains an instant and a time zone) instead of transforming it to a Date (which loses the timezone information), or use a SimpleDateFormat configured with the timezone you want to display the java.util.Date to a string in the wanted time zone.
Joda Time provides a quality replacement for the Java date and time classes. The design allows for multiple calendar systems, while still providing a simple API. Converting a Joda DateTime object from one timezone to another is pretty easy and saves you quite a number of lines of code. See method below.
public static Date convertJodaTimezone(LocalDateTime date, String srcTz, String destTz) {
DateTime srcDateTime = date.toDateTime(DateTimeZone.forID(srcTz));
DateTime dstDateTime = srcDateTime.withZone(DateTimeZone.forID(destTz));
return dstDateTime.toLocalDateTime().toDateTime().toDate();
}
Since Joda Time has its own class for storing Date and Calendar objects, the DateTime class has its own toDate() method for converting it to a java.util.Date.
For further example check this link
I reused your code and did some changes. The commented lines were the previous implementation so that you can compare the difference with the new implementation.
Date dateIn = new Date();
DateTime dateTimeUtc = new DateTime( dateIn, DateTimeZone.UTC );
System.out.println("date time utc : " + dateTimeUtc);
DateTimeZone timeZoneLos_Angeles = DateTimeZone.forID( "America/Los_Angeles" ); // Adjust time zone to United States.
//DateTime dateTimeLos_Angeles = dateTimeUtc.withZone( timeZoneLos_Angeles );
DateTime dateTimeLos_Angeles = dateTimeUtc.withZone(timeZoneLos_Angeles);
//System.out.println("los angeles date time : " + dateTimeLos_Angeles.toDate());
System.out.println("los angeles date time : " + dateTimeLos_Angeles.toLocalDateTime().toDate());
DateTimeZone timeZoneMalaysia = DateTimeZone.forID( "Asia/Singapore" );
DateTime dateTimeKL = dateTimeUtc.withZone(timeZoneMalaysia);
//System.out.println("KL date time : " + dateTimeKL.toDate());
System.out.println("KL date time : " + dateTimeKL.toLocalDateTime().toDate());
//Date newDate = dateTimeKL.toDate();
Date newDate = dateTimeKL.toLocalDateTime().toDate();
System.out.println("after convert to j.u.Date : " + newDate);
I hope this one works for you. If you can optimize this code further then great. Cheers!
This is continuation to one of my previous question where I am not able to parse the date which is resolved now. In the below code, I have a date string and I know the time zone for the date string even though the string itself doesn't contain it. Then I need to convert the date into EST time zone.
String clientTimeZone = "CST6CDT";
String value = "Dec 29 2014 11:36PM";
value=StringUtils.replace(value, " ", " ");
DateTimeFormatter df = DateTimeFormat.forPattern("MMM dd yyyy hh:mma").withZone(DateTimeZone.forID(clientTimeZone));
DateTime temp = df.parseDateTime(value);
System.out.println(temp.getZone().getID());
Timestamp ts1 = new Timestamp(temp.getMillis());
DateTime date = temp.withZoneRetainFields(DateTimeZone.forID("EST"));//withZone(DateTimeZone.forID("EST"));
Timestamp ts = new Timestamp(date.getMillis());
System.out.println(ts1+"="+ts);
When I am running the code I am expecting ts1 to remain same and ts to be up by 1 hr. But iam getting below which I don't understand. I thought EST is one hour ahead of CST and so if it is 11 in CST, it should be 12 in EST. Also there seems to be offset by about eleven and half hours. Any clues on what I am missing.
2014-12-30 11:06:00.0=2014-12-30 10:06:00.0
I think the below code will help you.
String clientTimeZone = "CST6CDT";
String toStimeZone = "EST";
String value = "Dec 29 2014 11:36PM";
TimeZone fromTimeZone = TimeZone.getTimeZone(clientTimeZone);
TimeZone toTimeZone = TimeZone.getTimeZone(toStimeZone);
Calendar calendar = Calendar.getInstance();
calendar.setTimeZone(fromTimeZone);
SimpleDateFormat sf = new SimpleDateFormat("MMM dd yyyy KK:mma");
Date date = sf.parse(value);
calendar.setTime(date);
System.out.println(date);
calendar.add(Calendar.MILLISECOND, fromTimeZone.getRawOffset() * -1);
if (fromTimeZone.inDaylightTime(calendar.getTime())) {
calendar.add(Calendar.MILLISECOND, calendar.getTimeZone().getDSTSavings() * -1);
}
calendar.add(Calendar.MILLISECOND, toTimeZone.getRawOffset());
if (toTimeZone.inDaylightTime(calendar.getTime())) {
calendar.add(Calendar.MILLISECOND, toTimeZone.getDSTSavings());
}
System.out.println(calendar.getTime());
Copied from : http://singztechmusings.wordpress.com/2011/06/23/java-timezone-correctionconversion-with-daylight-savings-time-settings/
The method withZoneRetainFields() preserves the fields in the timezone CST (= UTC-06) hence your local timestamp (as LocalDateTime) but combines it with a different timezone (EST = UTC-05) which is one hour ahead in offset and result in a different instant. You should it interprete it this way: The same local time happens one hour earlier in New York compared to Chicago.
The rule is to subtract positive offsets and to add negative offsets in order to make timestamp representations of instants comparable (normalizing to UTC offset).
Alternatively: Maybe you don't want this but want to preserve the instant instead of the local fields. In this case you have to use the method withZone().
Side notice: Effectively, you compare the instants represented by the variables temp and date and finally use your default timezone to print these instants in the JDBC-escape-format (explanation - you implicitly use Timestamp.toString()). I would rather recommend to use a dedicated instant formatter for this purpose or simpler (to have the offsets in focus):
System.out.println(temp.toInstant() + " = " + date.toInstant());
I am trying to convert between a date printed out in an EST timezone into a date printed out in GMT/UTC
package com.stefano;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.TimeZone;
public class MainEntry {
/**
* #param args
* #throws ParseException
*/
public static void main(String[] args) throws ParseException {
String dateTime = "1307011200"; //12:00PM 01 July 2013
System.out.println("Input -> " + dateTime);
SimpleDateFormat format = new SimpleDateFormat("yyMMddHHmm");
format.setTimeZone(TimeZone.getTimeZone("EST"));
Date date = format.parse(dateTime);
System.out.println("Intermediate -> " + date);
format.setTimeZone(TimeZone.getTimeZone("GMT"));
System.out.println("Output -> " + format.format(date));
}
}
The output it gives is:
Input -> 1307011200
Intermediate -> Mon Jul 01 17:00:00 BST 2013
Output -> 1307011600
Even though the time difference between EST and GMT is always 5, it is somehow getting involved with BST.
I cannot use Joda-Time.
The javadoc of the SimpleDateFormat.parse(String) method refers to the parse(String, ParsePosition) method, that says:
This parsing operation uses the calendar to produce a Date. As a result, the calendar's date-time fields and the TimeZone value may have been overwritten, depending on subclass implementations. Any TimeZone value that has previously been set by a call to setTimeZone may need to be restored for further operations.
According to this you can't use this method to tell the SimpleDateFormat which timezone
the given date is in.
You can fix this method like this:
String dateTime = "1307011200"; // 12:00PM 01 July 2013
dateTime += " EST"; // append the timezone information to the input string
System.out.println("Input -> " + dateTime);
SimpleDateFormat format = new SimpleDateFormat("yyMMddHHmm z"); // tell the formatter to look for the timezone info
Date date = format.parse(dateTime);
System.out.println("Intermediate -> " + date);
format.setTimeZone(TimeZone.getTimeZone("GMT"));
System.out.println("Output -> " + format.format(date));
This will also print the Date object using your local timezone, but it shows a way to parse the dateTime string using a given timezone.
The answer by zovits is correct.
US East Coast Offset
If by EST you mean the east coast of the United States (and parts of Canada), then your statement the time difference between EST and GMT is always 5 is incorrect. With Daylight Saving Time (DST), the offset may be -05:00 or -04:00. Indeed, your specified date-time does have DST in effect.
Avoid 3-4 Letter Time Zone Codes
Those three or four letter time zone codes are neither standardized nor unique. Avoid them. Use proper time zone names, most of which are continent+city.
Comparison To Joda-Time
For comparison, here is some Joda-Time example code. The java.util.Date & .Calendar classes bundled with Java are so notoriously troublesome that every Java programmer should move to either Joda-Time or the new Java 8 java.time package (inspired by Joda-Time, defined by JSR 310).
While a java.util.Date seems to have a time zone but actually does not, note that a Joda-Time DateTime does truly know its own assigned time zone.
Joda-Time uses the ISO 8601 standard for its defaults. You can use other formats as well, as seen with the Montréal example below.
Example Code
String input = "1307011200"; //12:00PM 01 July 2013
DateTimeFormatter formatterSmooshed = DateTimeFormat.forPattern( "yyMMddHHmm" );
DateTimeZone timeZoneNewYork = DateTimeZone.forID( "America/New_York" );
DateTime dateTimeNewYork = formatterSmooshed.withZone( timeZoneNewYork ).parseDateTime( input );
DateTime dateTimeUtc = dateTimeNewYork.withZone( DateTimeZone.UTC );
String outputMontréal = DateTimeFormat.forStyle( "FF" ).withLocale( Locale.CANADA_FRENCH ).print( dateTimeNewYork );
String outputSmooshed = formatterSmooshed.print( dateTimeNewYork ); // Expect same as input.
Dump to console…
System.out.println( "input: " + input );
System.out.println( "dateTimeNewYork: " + dateTimeNewYork );
System.out.println( "dateTimeUtc: " + dateTimeUtc );
System.out.println( "outputMontréal: " + outputMontréal );
System.out.println( "outputSmooshed: " + outputSmooshed );
When run…
input: 1307011200
dateTimeNewYork: 2013-07-01T12:00:00.000-04:00
dateTimeUtc: 2013-07-01T16:00:00.000Z
outputMontréal: lundi 1 juillet 2013 12 h 00 EDT
outputSmooshed: 1307011200