prestodb/presto · error · UnsupportedOperationException
toEpochMillis is not supported for TIMESTAMP(
Error message
toEpochMillis is not supported for TIMESTAMP(
What it means
toEpochMillis converts the packed long representation of a TIMESTAMP to epoch milliseconds, but only short precisions (p=0..6) fit in the 64-bit representation. Long precisions (p=7-12) need 128-bit storage, so calling this helper on them throws UnsupportedOperationException.
Source
Thrown at presto-common/src/main/java/com/facebook/presto/common/type/TimestampType.java:180
// Floor modulo handles negative (pre-1970) timestamps correctly; Java % does not.
public int getNanos(long timestamp)
{
long fractional = floorMod(timestamp, PRECISION_SCALE[precision]);
long scale = PRECISION_SCALE[precision];
// For p <= 9, scale <= 1e9: multiply up to nanoseconds.
// For p > 9, scale > 1e9: dividing avoids integer overflow; scale is always a multiple of 1e9.
if (scale <= 1_000_000_000L) {
return (int) (fractional * (1_000_000_000L / scale));
}
return (int) (fractional / (scale / 1_000_000_000L));
}
// Supported for all short precisions (p=0 through p=6, i.e. isShort()==true).
// Long precisions (p=7-12) require a 128-bit representation and are not yet supported.
public long toEpochMillis(long timestamp)
{
if (!isShort()) {
throw new UnsupportedOperationException(
"toEpochMillis is not supported for TIMESTAMP(" + precision + ")");
}
return getEpochSecond(timestamp) * 1_000L + getNanos(timestamp) / 1_000_000;
}
// Supported for all short precisions (p=0 through p=6, i.e. isShort()==true).
// Long precisions (p=7-12) require a 128-bit representation and are not yet supported.
public long toEpochMicros(long timestamp)
{
if (!isShort()) {
throw new UnsupportedOperationException(
"toEpochMicros is not supported for TIMESTAMP(" + precision + ")");
}
return getEpochSecond(timestamp) * 1_000_000L + getNanos(timestamp) / 1_000;
}
public long fromEpochComponents(long epochSecond, int nanos)
{View on GitHub (pinned to 55bb57d202)
Solutions
- Guard with type.isShort() before calling and handle long precisions separately.
- Migrate the column to a short precision (e.g. TIMESTAMP(6)) if millisecond conversion is needed.
- Await/use the 128-bit (LongTimestamp) API path for p=7-12 values.
Example fix
// before
long ms = type.toEpochMillis(block.getLong(position));
// after
if (!type.isShort()) {
throw new UnsupportedOperationException("Use 128-bit path for " + type.getDisplayName());
}
long ms = type.toEpochMillis(block.getLong(position)); Defensive patterns
Strategy: type-guard
Validate before calling
if (!timestampType.isShort()) {
throw new IllegalStateException("toEpochMillis requires short precision, got " + timestampType.getPrecision());
} Type guard
boolean supportsEpochMillis(TimestampType t) { return t.isShort(); } Try / catch
try {
ms = type.toEpochMillis(packed);
} catch (UnsupportedOperationException e) {
ms = convertLongTimestampToMillis(packedLongTimestamp); // 128-bit fallback
} Prevention
- Gate all epoch-helper calls behind isShort().
- Keep short/long timestamp handling in separate code paths.
- Add tests covering precision 7 to catch regressions early.
When it happens
Trigger: Calling toEpochMillis(timestamp) on a TimestampType instance with precision 7 through 12 (isShort() == false).
Common situations: Connector/reader code that assumes all TIMESTAMP values are longs, encountering new long-precision columns introduced by newer type-system support.
Understand the failure class
Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.
Related errors
- toEpochMicros is not supported for TIMESTAMP(
- getObjectValue is not supported for TIMESTAMP(
- fromEpochComponents is not supported for TIMESTAMP(
- Unsupported precision for TimeUnit conversion: TIMESTAMP(
- SingleMapBlock does not support appendNull()
AI-assisted analysis of prestodb/presto@55bb57d202 (2026-09-04).
Data as JSON: /api/errors/0ec372d5b1866e58.
Report an issue: GitHub.