Welcome to the new DOCS.vastdata.com. We've added new menus and a version selector, plus new persona and resource pages to help customers get started. Looking for a previous article? Use the docs search.

DESCRIBE

Prev Next

Applies to VAST Cluster 5.5.

Shows a table's columns and their types.

Syntax

DESCRIBE [TABLE] "<bucket>/<schema>".<table>
SHOW "<bucket>/<schema>".<table>

Parameters and rules

DESCRIBE, DESCRIBE TABLE and SHOW return the same result: one row per column, with six columns:

Result column Holds
column_name The column's name
column_type Its SQL type, for example BIGINT, VARCHAR, STRUCT(lat DOUBLE) or TIMESTAMP WITH TIME ZONE
null, key, default, extra In the captures, null was always YES and the others empty: the Query Engine has no NOT NULL, keys or defaults.

What DESCRIBE doesn't show:

  • The sort key of a sorted table. Use the Python SDK's table metadata (data modeling).
  • The vector index settings (metric and quantization). The vector column shows as VECTOR(FLOAT, <dim>); see vector search SQL.
  • Whether a column can be read through the Query Engine. MAP and TIMESTAMP WITH TIME ZONE columns are listed, but selecting them fails; see data types in SQL.

DESCRIBE of a query, such as DESCRIBE (SELECT rowid FROM ...), fails with an internal error message. Use typeof() instead: SELECT typeof(rowid) FROM <table> LIMIT 1.

If a row filter or column mask applies to you on the table, DESCRIBE fails like any other statement on it (vector search security). With a column deny rule, DESCRIBE lists only the columns you may read.

What happens on the cluster

DESCRIBE reads the table's definition from the database's catalog. It reads no rows.

Example

The examples use the run() helper and the environment variables described in the SQL reference. This block connects, and creates the schema docs_sql_describe with a sorted table:

import os
import re

import adbc_driver_manager
import adbc_driver_manager.dbapi as dbapi
import adbc_driver_vastdb

BUCKET = os.environ["VASTDB_BUCKET"]
SCHEMA = f'"{BUCKET}/docs_sql_describe"'

def connect(autocommit=True):
    return dbapi.connect(
        driver=adbc_driver_vastdb.get_driver_path(),
        db_kwargs={
            "vast.db.endpoint": os.environ["QE_ENDPOINT"],
            "vast.db.access_key": os.environ["AWS_ACCESS_KEY_ID"],
            "vast.db.secret_key": os.environ["AWS_SECRET_ACCESS_KEY"],
        },
        autocommit=autocommit,
    )

def server_message(e):
    """The server's message in a driver error, without the request ID or the echoed statement."""
    text = re.sub(r"\[req=0x[0-9a-f]+\]: ", "", str(e))
    found = (re.search(r'message: "(.*?)", request_id', text, re.S)
             or re.search(r"description: (.*)\)", text, re.S))
    message = found.group(1) if found else text.strip().splitlines()[-1]
    message = re.sub(r"^Plan query: '.*?' failed with: ", "", message, flags=re.S)
    message = re.split(r"\\n|\n", message)[0].replace('\\"', '"')
    return message.replace(BUCKET, "<bucket>")

def run(sql):
    """Run one statement. Print the rows it returns, or the error."""
    try:
        with conn.cursor() as cur:
            cur.execute(sql)
            rows = cur.fetchall() if cur.description else []
    except (adbc_driver_manager.Error, OSError) as e:
        print(f"{type(e).__name__}: {server_message(e)}")
    else:
        print(rows)

conn = connect()
run(f"CREATE SCHEMA IF NOT EXISTS {SCHEMA}")
run(f"CREATE TABLE IF NOT EXISTS {SCHEMA}.readings "
    "(id BIGINT, city VARCHAR, taken_at TIMESTAMP, location STRUCT(lat DOUBLE, lon DOUBLE), "
    "CONSTRAINT readings_sk SORT KEY (id))")
[]
[]

The three forms return the same rows. The sort key isn't listed:

run(f"DESCRIBE {SCHEMA}.readings")
run(f"DESCRIBE TABLE {SCHEMA}.readings")
run(f"SHOW {SCHEMA}.readings")
[('id', 'BIGINT', 'YES', None, None, None), ('city', 'VARCHAR', 'YES', None, None, None), ('taken_at', 'TIMESTAMP', 'YES', None, None, None), ('location', 'STRUCT(lat DOUBLE, lon DOUBLE)', 'YES', None, None, None)]
[('id', 'BIGINT', 'YES', None, None, None), ('city', 'VARCHAR', 'YES', None, None, None), ('taken_at', 'TIMESTAMP', 'YES', None, None, None), ('location', 'STRUCT(lat DOUBLE, lon DOUBLE)', 'YES', None, None, None)]
[('id', 'BIGINT', 'YES', None, None, None), ('city', 'VARCHAR', 'YES', None, None, None), ('taken_at', 'TIMESTAMP', 'YES', None, None, None), ('location', 'STRUCT(lat DOUBLE, lon DOUBLE)', 'YES', None, None, None)]

To see the type of an expression, use typeof():

run(f"INSERT INTO {SCHEMA}.readings VALUES (1, 'Lisbon', TIMESTAMP '2026-01-01 10:00:00', {{'lat': 38.7, 'lon': -9.1}})")
run(f"SELECT typeof(rowid), typeof(location.lat) FROM {SCHEMA}.readings LIMIT 1")
[(1,)]
[('DECIMAL(38,0)', 'DOUBLE')]

Clean up:

run(f"DROP TABLE IF EXISTS {SCHEMA}.readings")
run(f"DROP SCHEMA IF EXISTS {SCHEMA}")
conn.close()
[]
[]

Errors

You wrote Message
DESCRIBE (SELECT ...) An internal error message that doesn't say what's wrong. Use typeof().

Trino and Spark

Trino and Spark have their own DESCRIBE, and Trino's SHOW CREATE TABLE also shows the sort columns; see Trino and Spark.

See also: SHOW, data types in SQL.