How to retrieve results as Arrow tables¶
Query results can be fetched as a PyArrow Table instead of individual
Row objects. This gives you zero-copy interop with
Pandas and Polars, and works with any ADBC-backed pool (Snowflake,
Databricks, DuckDB).
Fetch an Arrow table¶
Call fetch_arrow_table() on the cursor
returned by .execute():
from semolina import SemanticView, Metric, Dimension
class Sales(SemanticView, view="sales"):
revenue = Metric()
country = Dimension()
cursor = (
Sales.query()
.metrics(Sales.revenue)
.dimensions(Sales.country)
.execute()
)
table = cursor.fetch_arrow_table()
print(type(table))
# <class 'pyarrow.lib.Table'>
print(table.schema)
# country: string
# revenue: int64
fetch_arrow_table() delegates to the underlying ADBC cursor. No
extra dependencies beyond the backend driver are needed.
Convert to a Pandas DataFrame¶
PyArrow tables have a built-in to_pandas() method:
df = table.to_pandas()
print(type(df))
# <class 'pandas.core.frame.DataFrame'>
This requires pandas (pip install pandas). PyArrow uses zero-copy
conversion where column types allow it; some types require a copy.
Convert to a Polars DataFrame¶
Polars accepts PyArrow tables directly through pl.from_arrow():
import polars as pl
df = pl.from_arrow(table)
print(type(df))
# <class 'polars.dataframe.frame.DataFrame'>
This requires polars (pip install polars). The conversion is
zero-copy and does not depend on pandas.
When to use Arrow output¶
Use
fetch_arrow_table()when passing results to Pandas, Polars, or other Arrow-compatible tools.Use
fetchall_rows()when working with individual rows or serializing to JSON.Arrow output skips the per-row Python object creation that
fetchall_rows()performs, which matters for larger result sets.
See also¶
How to stream large results – stream Arrow batches and iterate rows lazily
How to serialize results for API responses – serialize Row objects to dictionaries and JSON
How to build queries – build queries and access results
fetch_arrow_table()– API reference