> For the complete documentation index, see [llms.txt](https://docs.scanner.dev/scanner/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.scanner.dev/scanner/using-scanner-complete-feature-reference/data-ingestion/sources/snowflake.md).

# Snowflake

This guide walks through how to set up Snowflake as a log source in Scanner Collect, using direct API integration to query login history, query history, and session history tables. Scanner will authenticate using key-pair authentication and pull logs from your Snowflake account usage tables.

We'll assume that you want Scanner to both store the logs in S3 and index them for search and detection.

## Prerequisites

Before you begin, make sure you have:

* Permissions to create users and roles in your Snowflake instance
* Permissions to grant access to the `SNOWFLAKE.ACCOUNT_USAGE` schema
* Permissions in Scanner to create the integration
* Your Snowflake [account identifier](https://docs.snowflake.com/user-guide/gen-conn-config#using-sql-commands-to-get-connection-settings) in the `organization_name-account_name` format
* A warehouse name where Scanner will execute queries

## Create a Collect Rule

{% stepper %}
{% step %}

### Begin Setup

In the Scanner UI, go to the Collect tab.

* From the Overview page click the '+' icon in the upper right corner
* Select create new **Collect Rule**
* Choose **Snowflake**.
* Select the **Log Type**:
  * **Snowflake: Login History** - captures authentication events from `SNOWFLAKE.ACCOUNT_USAGE.LOGIN_HISTORY`
  * **Snowflake: Query History** - captures query execution events from `SNOWFLAKE.ACCOUNT_USAGE.QUERY_HISTORY`
  * **Snowflake: Session History** - captures session events from `SNOWFLAKE.ACCOUNT_USAGE.SESSIONS`
    {% endstep %}

{% step %}

### Configuration

* Set a **Display Name**, such as `my-org-snowflake-login-history`.
  {% endstep %}

{% step %}

### Authenticate with Snowflake

* If you've previously created a Snowflake connection, select it from the list and continue.
* Otherwise, select **New Snowflake Connection** and complete both sections below:

<details>

<summary>Create a Snowflake Integration in Scanner</summary>

In the modal:

* Enter a **Connection Name** for this integration.
* Enter your [**Account Identifier**](https://docs.snowflake.com/user-guide/gen-conn-config#using-sql-commands-to-get-connection-settings) in the `organization_name-account_name` format. You can retrieve this by running the following SQL in your Snowflake instance:

```sql
SELECT CURRENT_ORGANIZATION_NAME() || '-' || CURRENT_ACCOUNT_NAME();
```

* Enter a **Username** for the Scanner service account (e.g. `scanner_service_account`). You'll create this user in Snowflake in the next section.

Click **Connect**.

After creating the integration, Scanner will display:

* The **Username** you chose
* The **Public Key** that Scanner generated for this integration

Copy the public key to use in the following section.

</details>

<details>

<summary>Create a Service Account in Snowflake</summary>

In your Snowflake instance, run the following script as an admin.

{% hint style="info" %}
If you need to find your integration details again (username and public key), go to **Integrations** in your team's settings and select your Snowflake connection.
{% endhint %}

Before running the script, replace the placeholders:

* `scanner_service_account` → the username you chose in the previous section
* `scanner_service_account_role` → a role name of your choice for Scanner
* `COMPUTE_WH` → the warehouse where Scanner will run queries
* `PUBLIC_KEY` → the public RSA key from the previous section

```sql
-- Set variables
SET scanner_user = 'scanner_service_account'; -- REPLACE with your chosen username
SET scanner_role = 'scanner_service_account_role'; -- REPLACE with a role name of your choice
SET warehouse_name = 'COMPUTE_WH'; -- REPLACE with the warehouse of your choice

-- 1. Create the role
CREATE ROLE IF NOT EXISTS IDENTIFIER($scanner_role);

-- 2. Grant usage on the SNOWFLAKE database and ACCOUNT_USAGE schema
GRANT IMPORTED PRIVILEGES ON DATABASE SNOWFLAKE TO ROLE IDENTIFIER($scanner_role);

-- 3. Grant usage on a specific warehouse
GRANT USAGE ON WAREHOUSE IDENTIFIER($warehouse_name) TO ROLE IDENTIFIER($scanner_role);

-- 4. Create the service account user with RSA public key
CREATE USER IF NOT EXISTS IDENTIFIER($scanner_user)
  DEFAULT_ROLE = $scanner_role
  DEFAULT_WAREHOUSE = $warehouse_name
  RSA_PUBLIC_KEY = 'PUBLIC_KEY'; -- REPLACE with the public key from Step 4

-- 5. Grant the role to the user
GRANT ROLE IDENTIFIER($scanner_role) TO USER IDENTIFIER($scanner_user);
```

{% hint style="info" %}
Scanner will always connect using the default role and default warehouse configured for this user. To change the warehouse later, run:

`ALTER USER scanner_service_account SET DEFAULT_WAREHOUSE = new_warehouse_name;`
{% endhint %}

Once you've completed the Snowflake setup, close the setup dialog.

</details>
{% endstep %}

{% step %}

### Logs Destination

* Choose the S3 Bucket where the raw Snowflake logs should be stored.
* (Optional) Enter a Key Prefix to organize the data path in your bucket.
  {% endstep %}

{% step %}

### Review and Create

* Review all configuration settings. Any errors and/or missing fields must be resolved before completion.
  {% endstep %}
  {% endstepper %}

## Create an Index Rule

With the Collect Rule created, Scanner will poll the selected Snowflake account usage table every **5 minutes**, writing new events to your S3 bucket. Create an Index Rule to make them searchable for fast search and detections.

{% content-ref url="/pages/Gem9jwD4aqayN3OiChpN" %}
[Create an Index Rule](/scanner/using-scanner-complete-feature-reference/data-ingestion/create-an-index-rule.md)
{% endcontent-ref %}

### Snowflake Defaults

When you create the Index Rule from the Collect Rule, the following defaults are pre-populated:

* **Transformations**: Add Metadata, Parse JSON Columns, ECS Normalization: Snowflake
* **Timestamp Field**:
  * `.EVENT_TIMESTAMP` for Snowflake: Login History
  * `.END_TIME` for Snowflake: Query History
  * `.CREATED_ON` for Snowflake: Session History


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.scanner.dev/scanner/using-scanner-complete-feature-reference/data-ingestion/sources/snowflake.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
