prestodb/presto · error · PrestoException

INVALID_ARGUMENTS

INVALID_ARGUMENTS

Error message

Table version AS OF/BEFORE expression cannot be NULL for %s

What it means

The expression in a FOR TIMESTAMP/VERSION AS OF/BEFORE clause must evaluate to a known (non-NULL) constant. After analyzing the state expression, if its type is UNKNOWN (e.g. a NULL literal), Presto throws INVALID_ARGUMENTS because a NULL version or timestamp cannot identify a table snapshot.

Source

Thrown at presto-main-base/src/main/java/com/facebook/presto/sql/analyzer/StatementAnalyzer.java:2587

            switch (type) {
                case TIMESTAMP:
                    return VersionType.TIMESTAMP;
                case VERSION:
                    return VersionType.VERSION;
            }
            throw new SemanticException(NOT_SUPPORTED, "Table version type %s not supported." + type);
        }

        private Optional<TableHandle> processTableVersion(Table table, QualifiedObjectName name, Optional<Scope> scope)
        {
            Expression stateExpr = table.getTableVersionExpression().get().getStateExpression();
            TableVersionType tableVersionType = table.getTableVersionExpression().get().getTableVersionType();
            TableVersionOperator tableVersionOperator = table.getTableVersionExpression().get().getTableVersionOperator();
            ExpressionAnalysis expressionAnalysis = analyzeExpression(stateExpr, scope.get());
            analysis.recordSubqueries(table, expressionAnalysis);
            Type stateExprType = expressionAnalysis.getType(stateExpr);
            if (stateExprType == UNKNOWN) {
                throw new PrestoException(StandardErrorCode.INVALID_ARGUMENTS, format("Table version AS OF/BEFORE expression cannot be NULL for %s", name.toString()));
            }
            Object evalStateExpr = evaluateConstantExpression(stateExpr, stateExprType, metadata, session, analysis.getParameters());
            if (tableVersionType == TIMESTAMP) {
                if (!(stateExprType instanceof TimestampWithTimeZoneType || stateExprType instanceof TimestampType
                        || stateExprType instanceof BigintType || stateExprType instanceof VarcharType)) {
                    throw new SemanticException(TYPE_MISMATCH, stateExpr,
                            "Type %s is invalid. Supported table version AS OF/BEFORE expression type is Timestamp, Timestamp with Time Zone, BIGINT, or VARCHAR.",
                            stateExprType.getDisplayName());
                }
            }
            if (tableVersionType == VERSION) {
                if (!(stateExprType instanceof BigintType || stateExprType instanceof VarcharType)) {
                    throw new SemanticException(TYPE_MISMATCH, stateExpr,
                            "Type %s is invalid. Supported table version AS OF/BEFORE expression type is BIGINT or VARCHAR",
                            stateExprType.getDisplayName());
                }
            }

View on GitHub (pinned to 55bb57d202)

Solutions

  1. Provide a concrete non-NULL timestamp or version value in the AS OF/BEFORE clause
  2. Substitute any session/prepare parameters with actual values before running the query
  3. If the value may be missing at runtime, branch in application code and only include the FOR clause when a valid value exists

Example fix

// before
SELECT * FROM t FOR TIMESTAMP AS OF ?; -- parameter bound to NULL
// after
SELECT * FROM t FOR TIMESTAMP AS OF TIMESTAMP '2024-01-01 00:00:00';
Defensive patterns

Strategy: validation

Validate before calling

if (versionValue == null) {
    throw new IllegalArgumentException("AS OF/BEFORE value must be non-NULL");
}

Type guard

function hasVersionValue(v) {
    return v !== null && v !== undefined;
}

Try / catch

try {
    return session.execute(query);
} catch (PrestoException e) {
    if (e.getStandardErrorCode() == INVALID_ARGUMENTS) {
        // substitute a concrete timestamp/version and retry
    }
    throw e;
}

Prevention

When it happens

Trigger: SELECT * FROM t FOR TIMESTAMP AS OF NULL; or an expression that folds to NULL/UNKNOWN type (e.g. a constant-folding NULL parameter). Detected by stateExprType == UNKNOWN right after analyzeExpression.

Common situations: Passing NULL via a session parameter used in AS OF clauses; template-generated SQL with an unset timestamp placeholder; copy-paste queries with placeholder values not filled in.

Related errors


AI-assisted analysis of prestodb/presto@55bb57d202 (2026-09-04). Data as JSON: /api/errors/eeb4a7c8e3be4326. Report an issue: GitHub.