diff --git ql/src/java/org/apache/hadoop/hive/ql/io/parquet/timestamp/NanoTimeUtils.java ql/src/java/org/apache/hadoop/hive/ql/io/parquet/timestamp/NanoTimeUtils.java index bf78d8cc5b..3760028a9f 100644 --- ql/src/java/org/apache/hadoop/hive/ql/io/parquet/timestamp/NanoTimeUtils.java +++ ql/src/java/org/apache/hadoop/hive/ql/io/parquet/timestamp/NanoTimeUtils.java @@ -27,87 +27,87 @@ * This utilizes the Jodd library. */ public class NanoTimeUtils { - static final long NANOS_PER_HOUR = TimeUnit.HOURS.toNanos(1); - static final long NANOS_PER_MINUTE = TimeUnit.MINUTES.toNanos(1); - static final long NANOS_PER_SECOND = TimeUnit.SECONDS.toNanos(1); - static final long NANOS_PER_DAY = TimeUnit.DAYS.toNanos(1); - - private static final ThreadLocal parquetGMTCalendar = new ThreadLocal(); - private static final ThreadLocal parquetLocalCalendar = new ThreadLocal(); - - private static Calendar getGMTCalendar() { - //Calendar.getInstance calculates the current-time needlessly, so cache an instance. - if (parquetGMTCalendar.get() == null) { - parquetGMTCalendar.set(Calendar.getInstance(TimeZone.getTimeZone("GMT"))); - } - return parquetGMTCalendar.get(); - } - - private static Calendar getLocalCalendar() { - if (parquetLocalCalendar.get() == null) { - parquetLocalCalendar.set(Calendar.getInstance()); - } - return parquetLocalCalendar.get(); - } - - public static Calendar getCalendar(boolean skipConversion) { - Calendar calendar = skipConversion ? getLocalCalendar() : getGMTCalendar(); - calendar.clear(); // Reset all fields before reusing this instance - return calendar; - } - - public static NanoTime getNanoTime(Timestamp ts, boolean skipConversion) { - - Calendar calendar = getCalendar(skipConversion); - calendar.setTimeInMillis(ts.toEpochMilli()); - int year = calendar.get(Calendar.YEAR); - if (calendar.get(Calendar.ERA) == GregorianCalendar.BC) { - year = 1 - year; - } - JDateTime jDateTime = new JDateTime(year, - calendar.get(Calendar.MONTH) + 1, //java calendar index starting at 1. - calendar.get(Calendar.DAY_OF_MONTH)); - int days = jDateTime.getJulianDayNumber(); - - long hour = calendar.get(Calendar.HOUR_OF_DAY); - long minute = calendar.get(Calendar.MINUTE); - long second = calendar.get(Calendar.SECOND); - long nanos = ts.getNanos(); - long nanosOfDay = nanos + NANOS_PER_SECOND * second + NANOS_PER_MINUTE * minute + - NANOS_PER_HOUR * hour; - - return new NanoTime(days, nanosOfDay); - } - - public static Timestamp getTimestamp(NanoTime nt, boolean skipConversion) { - int julianDay = nt.getJulianDay(); - long nanosOfDay = nt.getTimeOfDayNanos(); - - long remainder = nanosOfDay; - julianDay += remainder / NANOS_PER_DAY; - remainder %= NANOS_PER_DAY; - if (remainder < 0) { - remainder += NANOS_PER_DAY; - julianDay--; - } - - JDateTime jDateTime = new JDateTime((double) julianDay); - Calendar calendar = getCalendar(skipConversion); - calendar.set(Calendar.YEAR, jDateTime.getYear()); - calendar.set(Calendar.MONTH, jDateTime.getMonth() - 1); //java calendar index starting at 1. - calendar.set(Calendar.DAY_OF_MONTH, jDateTime.getDay()); - - int hour = (int) (remainder / (NANOS_PER_HOUR)); - remainder = remainder % (NANOS_PER_HOUR); - int minutes = (int) (remainder / (NANOS_PER_MINUTE)); - remainder = remainder % (NANOS_PER_MINUTE); - int seconds = (int) (remainder / (NANOS_PER_SECOND)); - long nanos = remainder % NANOS_PER_SECOND; - - calendar.set(Calendar.HOUR_OF_DAY, hour); - calendar.set(Calendar.MINUTE, minutes); - calendar.set(Calendar.SECOND, seconds); - Timestamp ts = Timestamp.ofEpochMilli(calendar.getTimeInMillis(), (int) nanos); - return ts; - } + static final long NANOS_PER_HOUR = TimeUnit.HOURS.toNanos(1); + static final long NANOS_PER_MINUTE = TimeUnit.MINUTES.toNanos(1); + static final long NANOS_PER_SECOND = TimeUnit.SECONDS.toNanos(1); + static final long NANOS_PER_DAY = TimeUnit.DAYS.toNanos(1); + + private static final ThreadLocal parquetGMTCalendar = new ThreadLocal(); + private static final ThreadLocal parquetLocalCalendar = new ThreadLocal(); + + private static Calendar getGMTCalendar() { + //Calendar.getInstance calculates the current-time needlessly, so cache an instance. + if (parquetGMTCalendar.get() == null) { + parquetGMTCalendar.set(Calendar.getInstance(TimeZone.getTimeZone("GMT"))); + } + return parquetGMTCalendar.get(); + } + + private static Calendar getLocalCalendar() { + if (parquetLocalCalendar.get() == null) { + parquetLocalCalendar.set(Calendar.getInstance()); + } + return parquetLocalCalendar.get(); + } + + public static Calendar getCalendar(boolean skipConversion) { + Calendar calendar = skipConversion ? getLocalCalendar() : getGMTCalendar(); + calendar.clear(); // Reset all fields before reusing this instance + return calendar; + } + + public static NanoTime getNanoTime(Timestamp ts, boolean skipConversion) { + + Calendar calendar = getCalendar(skipConversion); + calendar.setTimeInMillis(ts.toEpochMilli()); + int year = calendar.get(Calendar.YEAR); + if (calendar.get(Calendar.ERA) == GregorianCalendar.BC) { + year = 1 - year; + } + JDateTime jDateTime = + new JDateTime(year, calendar.get(Calendar.MONTH) + 1, //java calendar index starting at 1. + calendar.get(Calendar.DAY_OF_MONTH)); + int days = jDateTime.getJulianDayNumber(); + + long hour = calendar.get(Calendar.HOUR_OF_DAY); + long minute = calendar.get(Calendar.MINUTE); + long second = calendar.get(Calendar.SECOND); + long nanos = ts.getNanos(); + long nanosOfDay = + nanos + NANOS_PER_SECOND * second + NANOS_PER_MINUTE * minute + NANOS_PER_HOUR * hour; + + return new NanoTime(days, nanosOfDay); + } + + public static Timestamp getTimestamp(NanoTime nt, boolean skipConversion) { + int julianDay = nt.getJulianDay(); + long nanosOfDay = nt.getTimeOfDayNanos(); + + long remainder = nanosOfDay; + julianDay += remainder / NANOS_PER_DAY; + remainder %= NANOS_PER_DAY; + if (remainder < 0) { + remainder += NANOS_PER_DAY; + julianDay--; + } + + JDateTime jDateTime = new JDateTime((double) julianDay); + Calendar calendar = getCalendar(skipConversion); + calendar.set(Calendar.YEAR, jDateTime.getYear()); + calendar.set(Calendar.MONTH, jDateTime.getMonth() - 1); //java calendar index starting at 1. + calendar.set(Calendar.DAY_OF_MONTH, jDateTime.getDay()); + + int hour = (int) (remainder / (NANOS_PER_HOUR)); + remainder = remainder % (NANOS_PER_HOUR); + int minutes = (int) (remainder / (NANOS_PER_MINUTE)); + remainder = remainder % (NANOS_PER_MINUTE); + int seconds = (int) (remainder / (NANOS_PER_SECOND)); + long nanos = remainder % NANOS_PER_SECOND; + + calendar.set(Calendar.HOUR_OF_DAY, hour); + calendar.set(Calendar.MINUTE, minutes); + calendar.set(Calendar.SECOND, seconds); + Timestamp ts = Timestamp.ofEpochMilli(calendar.getTimeInMillis(), (int) nanos); + return ts; + } }