Eugene
Eugene

Reputation: 60244

Why System.currentTimeMillis() generate incorrect long value?

It was discussed too many times, I know, but I can't get why the milliseconds generated by mine:

System.currentTimeMillis();

Or by:

Calendar.getInstance(TimeZone.getTimeZone("UTC")).getTimeInMillis()

Are not equal to what I see on www.epochconverter.com?

What I need is to merely generate a String of concrete format, but I've found out the milliseconds aren't right.

Just in case here is how I do it:

private static final String DATE_PATTERN = "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'";

public static String getCurrentTimestamp() {
        long time = System.currentTimeMillis();
        SimpleDateFormat sdf = new SimpleDateFormat(DATE_PATTERN);
        String lastModifiedTime = sdf.format(time);
        Logger.logVerbose(TAG, "Generated timestamp is " + lastModifiedTime);
        return lastModifiedTime;
    }

What I finally get is just a local time, but I need the only time which is pure UTC without conjunction with my timezone.

I've even checked it with SQLite (using the SELECT strftime('%s',timestring);) and got the correct milliseconds. Why then I got it incorrectly generated by those two statements I posted above? Thanks a lot in advance.

Upvotes: 1

Views: 1918

Answers (2)

JB Nizet
JB Nizet

Reputation: 692231

If you want the date format to format the time in the UTC zone, then use

sdf.setTimeZone(TimeZone.getTimeZone("UTC"));

Upvotes: 0

Peter Lawrey
Peter Lawrey

Reputation: 533880

Three things to consider

  • Java doesn't support UTC with leap seconds, only GMT. This is because OSes don't support it.
  • Your milli-seconds will be inaccurate unless you get the time off a satellite synchronized device.
  • You cannot run the command at exactly the same time so they will different some of the time.

But more importantly than that, if you don't set the tiemzone it will use the default time zone.

    SimpleDateFormat sdf = new SimpleDateFormat(DATE_PATTERN);
    // no time zone set so the default is used.
    String lastModifiedTime = sdf.format(time);

Instead you should add

    sdf.setTimeZone(TimeZone.getTimeZone("GMT"));

Adding a 'Z' to the format will change the timezone no more than adding 'T' to the format, it is just a letter you added.

Upvotes: 1

Related Questions