---
title: Data Warehouse Exports
description: "Export Statsig events, exposures, and metric data into your cloud data warehouse on a schedule for downstream BI, modeling, and custom analysis."
product: general
token_estimate: 3179
---
# Data Warehouse Exports

> For AI agents: a documentation index is available at [/llms.txt](/llms.txt). Append `.md` to any page URL for markdown, or send `Accept: text/markdown`.

## How data warehouse exports work

You can export your data from Statsig to your data warehouse using a data connection. The data connection lets you send exposures and events directly to your warehouse for further analysis. Statsig supports connections to Snowflake, Redshift, S3, BigQuery, and Databricks.

> **Info:**
>
> Data Warehouse Exports are an Enterprise-only feature. If you're on the Developer or Pro tiers and want to upgrade to Enterprise, reach out to the Statsig team [here](https://www.statsig.com/contact/demo) or through support.

## Set up a data warehouse export

1. Go to Statsig Console.
2. Navigate to the Help and Tools Section on the side navigation bar.
3. Go to "Exports List".

![Statsig Help and Tools menu showing Exports List option](https://docs.statsig.com/images/exports-list.png)

On the Exports page, you find an _Export History_ tab and a _Schedule Export_ tab. The _Export History_ tab lists all previous experimentation exports triggered from the _Experiment Results_ page. To export one-off experimentation results, refer to [Experiment Result Exports](https://docs.statsig.com/integrations/data-exports/experiment_result_exports).

Under the _Scheduled Export_ tab, set up a data warehouse connection. Configure the connection with the necessary credentials and grant Statsig Read, Write, and Delete permissions. The warehouse-specific tabs below show the fields Statsig requires and example SQL you can use to create each export table yourself.

![Scheduled export setup form for Snowflake connection with credential fields](https://docs.statsig.com/images/exports-schedule.png)

## Export table schema

Statsig can export both Exposures and Events to your destination. The exported columns are logically the same across SQL warehouses, but the physical types vary by warehouse. S3 is a file destination rather than a SQL table destination.

#### BigQuery

**Setup summary**

Configure:

- BigQuery Project ID
- BigQuery Dataset ID
- one destination table name per export type

Permissions:

- Grant the Statsig service account `BigQuery User` at the project level.
- Grant the same service account `BigQuery Data Editor` on the target dataset.

Statsig uses this access to create the table if needed and validate the connection by inserting and deleting a test row.

If you prefer to create the export tables yourself, you can use SQL like this:

```sql
CREATE TABLE IF NOT EXISTS `PROJECT_ID.DATASET_ID.EXPOSURES_TABLE` (
  company_id STRING,
  unit_id STRING,
  unit_type STRING,
  exposure_type STRING,
  name STRING,
  rule STRING,
  experiment_group STRING,
  first_exposure_utc TIMESTAMP,
  first_exposure_pst_date DATE,
  as_of_pst_date DATE,
  percent FLOAT64,
  rollout BIGINT,
  user_dimensions STRING,
  inserted_at TIMESTAMP,
  rule_name STRING,
  group_id STRING,
  non_analytics BOOLEAN
);
```

```sql
CREATE TABLE IF NOT EXISTS `PROJECT_ID.DATASET_ID.EVENTS_TABLE` (
  user_id STRING,
  stable_id STRING,
  custom_ids JSON,
  timestamp TIMESTAMP,
  event_name STRING,
  event_value STRING,
  user_object JSON,
  statsig_metadata JSON,
  company_metadata JSON
);
```

**Exposures**

Statsig doesn't export exposures from rules that are 0%/100%.

| Field name | Type | Mode |
| --- | --- | --- |
| company\_id | STRING | NULLABLE |
| unit\_id | STRING | NULLABLE |
| unit\_type | STRING | NULLABLE |
| exposure\_type | STRING | NULLABLE |
| name | STRING | NULLABLE |
| rule | STRING | NULLABLE |
| experiment\_group | STRING | NULLABLE |
| first\_exposure\_utc | TIMESTAMP | NULLABLE |
| first\_exposure\_pst\_date | DATE | NULLABLE |
| as\_of\_pst\_date | DATE | NULLABLE |
| percent | FLOAT64 | NULLABLE |
| rollout | BIGINT | NULLABLE |
| user\_dimensions | STRING | NULLABLE |
| inserted\_at | TIMESTAMP | NULLABLE |
| rule\_name | STRING | NULLABLE |
| group\_id | STRING | NULLABLE |
| non\_analytics | BOOLEAN | NULLABLE |

**Events**

| Field name | Type | Mode |
| --- | --- | --- |
| user\_id | STRING | NULLABLE |
| stable\_id | STRING | NULLABLE |
| custom\_ids | JSON | NULLABLE |
| timestamp | TIMESTAMP | NULLABLE |
| event\_name | STRING | NULLABLE |
| event\_value | STRING | NULLABLE |
| user\_object | JSON | NULLABLE |
| statsig\_metadata | JSON | NULLABLE |
| company\_metadata | JSON | NULLABLE |

#### Snowflake

**Setup summary**

Configure:

- Account Name
- Database Name
- Schema Name
- either Username and Password, or Private Key authentication
- one destination table name per export type

Permissions:

- The configured user must be able to create tables and insert/delete rows in the target database and schema.

If you prefer to create the export tables yourself, you can use SQL like this:

```sql
CREATE TABLE IF NOT EXISTS DATABASE_NAME.SCHEMA_NAME.EXPOSURES_TABLE (
  company_id STRING,
  unit_id STRING,
  unit_type STRING,
  exposure_type STRING,
  name STRING,
  rule STRING,
  experiment_group STRING,
  first_exposure_utc TIMESTAMP,
  first_exposure_pst_date DATE,
  as_of_pst_date DATE,
  percent DOUBLE,
  rollout BIGINT,
  user_dimensions STRING,
  inserted_at TIMESTAMP,
  rule_name STRING,
  group_id STRING,
  non_analytics BOOLEAN
);
```

```sql
CREATE TABLE IF NOT EXISTS DATABASE_NAME.SCHEMA_NAME.EVENTS_TABLE (
  user_id STRING,
  stable_id STRING,
  custom_ids STRING,
  timestamp TIMESTAMP,
  event_name STRING,
  event_value STRING,
  user_object STRING,
  statsig_metadata STRING,
  company_metadata STRING
);
```

**Exposures**

| Field name | Type | Mode |
| --- | --- | --- |
| company\_id | STRING | NULLABLE |
| unit\_id | STRING | NULLABLE |
| unit\_type | STRING | NULLABLE |
| exposure\_type | STRING | NULLABLE |
| name | STRING | NULLABLE |
| rule | STRING | NULLABLE |
| experiment\_group | STRING | NULLABLE |
| first\_exposure\_utc | TIMESTAMP | NULLABLE |
| first\_exposure\_pst\_date | DATE | NULLABLE |
| as\_of\_pst\_date | DATE | NULLABLE |
| percent | DOUBLE | NULLABLE |
| rollout | BIGINT | NULLABLE |
| user\_dimensions | STRING | NULLABLE |
| inserted\_at | TIMESTAMP | NULLABLE |
| rule\_name | STRING | NULLABLE |
| group\_id | STRING | NULLABLE |
| non\_analytics | BOOLEAN | NULLABLE |

**Events**

| Field name | Type | Mode |
| --- | --- | --- |
| user\_id | STRING | NULLABLE |
| stable\_id | STRING | NULLABLE |
| custom\_ids | STRING | NULLABLE |
| timestamp | TIMESTAMP | NULLABLE |
| event\_name | STRING | NULLABLE |
| event\_value | STRING | NULLABLE |
| user\_object | STRING | NULLABLE |
| statsig\_metadata | STRING | NULLABLE |
| company\_metadata | STRING | NULLABLE |

#### Redshift

**Setup summary**

Configure:

- Cluster Endpoint
- Username and Password
- Staging Schema
- one destination table name per export type

Permissions:

- The configured user must be able to create tables and insert/delete rows in the target database and schema.
- If your cluster isn't directly reachable, you can also configure SSH tunneling.

If you prefer to create the export tables yourself, you can use SQL like this:

```sql
CREATE TABLE IF NOT EXISTS "DATABASE_NAME"."STAGING_SCHEMA"."EXPOSURES_TABLE" (
  "company_id" VARCHAR,
  "unit_id" VARCHAR,
  "unit_type" VARCHAR,
  "exposure_type" VARCHAR,
  "name" VARCHAR,
  "rule" VARCHAR,
  "experiment_group" VARCHAR,
  "first_exposure_utc" TIMESTAMP,
  "first_exposure_pst_date" DATE,
  "as_of_pst_date" DATE,
  "percent" DOUBLE PRECISION,
  "rollout" BIGINT,
  "user_dimensions" VARCHAR,
  "inserted_at" TIMESTAMP,
  "rule_name" VARCHAR,
  "group_id" VARCHAR,
  "non_analytics" BOOLEAN
);
```

```sql
CREATE TABLE IF NOT EXISTS "DATABASE_NAME"."STAGING_SCHEMA"."EVENTS_TABLE" (
  "user_id" VARCHAR,
  "stable_id" VARCHAR,
  "custom_ids" VARCHAR,
  "timestamp" TIMESTAMP,
  "event_name" VARCHAR,
  "event_value" VARCHAR,
  "user_object" VARCHAR,
  "statsig_metadata" VARCHAR,
  "company_metadata" VARCHAR
);
```

> **Note:**
>
> The default size for VARCHAR is 256 and Statsig truncates all columns to 256 characters for Redshift. If you anticipate certain columns exceeding these limits, adjust accordingly and contact Statsig to remove these limits. Common longer columns are `user_dimensions` in exposures and `user_object`, `custom_ids`, and `company_metadata` in events.

**Exposures**

| Field name | Type | Mode |
| --- | --- | --- |
| company\_id | VARCHAR | NULLABLE |
| unit\_id | VARCHAR | NULLABLE |
| unit\_type | VARCHAR | NULLABLE |
| exposure\_type | VARCHAR | NULLABLE |
| name | VARCHAR | NULLABLE |
| rule | VARCHAR | NULLABLE |
| experiment\_group | VARCHAR | NULLABLE |
| first\_exposure\_utc | TIMESTAMP | NULLABLE |
| first\_exposure\_pst\_date | DATE | NULLABLE |
| as\_of\_pst\_date | DATE | NULLABLE |
| percent | DOUBLE PRECISION | NULLABLE |
| rollout | BIGINT | NULLABLE |
| user\_dimensions | VARCHAR | NULLABLE |
| inserted\_at | TIMESTAMP | NULLABLE |
| rule\_name | VARCHAR | NULLABLE |
| group\_id | VARCHAR | NULLABLE |
| non\_analytics | BOOLEAN | NULLABLE |

**Events**

| Field name | Type | Mode |
| --- | --- | --- |
| user\_id | VARCHAR | NULLABLE |
| stable\_id | VARCHAR | NULLABLE |
| custom\_ids | VARCHAR | NULLABLE |
| timestamp | TIMESTAMP | NULLABLE |
| event\_name | VARCHAR | NULLABLE |
| event\_value | VARCHAR | NULLABLE |
| user\_object | VARCHAR | NULLABLE |
| statsig\_metadata | VARCHAR | NULLABLE |
| company\_metadata | VARCHAR | NULLABLE |

#### Databricks

**Setup summary**

Configure:

- API Key
- Server Hostname
- HTTP Path
- Database
- one destination table name per export type

Permissions:

- The configured user or token must be able to create tables and insert/delete rows in the target database.

If you prefer to create the export tables yourself, you can use SQL like this:

```sql
CREATE TABLE IF NOT EXISTS DATABASE_NAME.EXPOSURES_TABLE (
  company_id STRING,
  unit_id STRING,
  unit_type STRING,
  exposure_type STRING,
  name STRING,
  rule STRING,
  experiment_group STRING,
  first_exposure_utc TIMESTAMP,
  first_exposure_pst_date DATE,
  as_of_pst_date DATE,
  percent DOUBLE,
  rollout BIGINT,
  user_dimensions STRING,
  inserted_at TIMESTAMP,
  rule_name STRING,
  group_id STRING,
  non_analytics BOOLEAN
);
```

```sql
CREATE TABLE IF NOT EXISTS DATABASE_NAME.EVENTS_TABLE (
  user_id STRING,
  stable_id STRING,
  custom_ids STRING,
  timestamp TIMESTAMP,
  event_name STRING,
  event_value STRING,
  user_object STRING,
  statsig_metadata STRING,
  company_metadata STRING
);
```

**Exposures**

| Field name | Type | Mode |
| --- | --- | --- |
| company\_id | STRING | NULLABLE |
| unit\_id | STRING | NULLABLE |
| unit\_type | STRING | NULLABLE |
| exposure\_type | STRING | NULLABLE |
| name | STRING | NULLABLE |
| rule | STRING | NULLABLE |
| experiment\_group | STRING | NULLABLE |
| first\_exposure\_utc | TIMESTAMP | NULLABLE |
| first\_exposure\_pst\_date | DATE | NULLABLE |
| as\_of\_pst\_date | DATE | NULLABLE |
| percent | DOUBLE | NULLABLE |
| rollout | BIGINT | NULLABLE |
| user\_dimensions | STRING | NULLABLE |
| inserted\_at | TIMESTAMP | NULLABLE |
| rule\_name | STRING | NULLABLE |
| group\_id | STRING | NULLABLE |
| non\_analytics | BOOLEAN | NULLABLE |

**Events**

| Field name | Type | Mode |
| --- | --- | --- |
| user\_id | STRING | NULLABLE |
| stable\_id | STRING | NULLABLE |
| custom\_ids | STRING | NULLABLE |
| timestamp | TIMESTAMP | NULLABLE |
| event\_name | STRING | NULLABLE |
| event\_value | STRING | NULLABLE |
| user\_object | STRING | NULLABLE |
| statsig\_metadata | STRING | NULLABLE |
| company\_metadata | STRING | NULLABLE |

#### S3

**Setup summary**

Configure:

- Region
- Bucket
- one folder name per export type

Permissions:

- Grant the Statsig IAM user bucket-level access to list the bucket and retrieve its location.
- Grant object-level read, write, and delete permissions, including multipart upload management.

S3 exports are file-based. Statsig writes export files to the configured bucket and folder for each export type. In the export UI, you configure the per-export destination as a folder rather than a table.

**Export outputs**

| Export type | Destination shape |
| --- | --- |
| Exposures | Files written to the configured folder in your bucket |
| Events | Files written to the configured folder in your bucket |

## Troubleshoot exports

Statsig can notify you if your data connection is failing. To enable notifications, go to _Settings > My Account > Email Notifications > Edit_ and select **Alerts** to subscribe.

If your exports are failing, confirm your warehouse is connected with up-to-date credentials and the necessary Read, Write, and Delete permissions.

