> ## Documentation Index
> Fetch the complete documentation index at: https://docs.getnao.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Configuration reference

# Configuration Reference

Complete reference for the `nao_config.yaml` file. This page is auto-generated from the Pydantic models in [`cli/nao_core/config/`](https://github.com/getnao/nao/tree/main/cli/nao_core/config).

Values wrapped in `${{ env('VAR') }}` or `{{ env('VAR') }}` are resolved from environment variables at load time.

## Resolving secrets

In addition to `env()`, any value in `nao_config.yaml` can pull a secret from AWS Secrets Manager or Kubernetes Secrets, so deployments can keep credentials out of plain environment variables:

| Resolver | Syntax                                | Notes                                                                                                                                                                                                                                                                                            |
| -------- | ------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `env`    | `{{ env('VAR') }}`                    | Resolves from an environment variable. Missing values become an empty string.                                                                                                                                                                                                                    |
| `aws`    | `{{ aws('secret_name/field') }}`      | Reads from AWS Secrets Manager. The reference is split on its **last** `/`: everything before is the secret id, everything after is the field. Full ARNs are supported (`{{ aws('arn:aws:secretsmanager:eu-west-1:123:secret:foo-AbCdEf/key') }}`) and the region is auto-detected from the ARN. |
| `k8s`    | `{{ k8s('namespace/secret/field') }}` | Reads from a Kubernetes Secret and base64-decodes the value. The namespace is optional (`{{ k8s('secret/field') }}`) and falls back to the pod namespace.                                                                                                                                        |

```yaml theme={null}
databases:
  - type: postgres
    name: prod-db
    user: ${{ env('DB_USER') }}
    password: '{{ aws("prod/db/credentials/password") }}'

slack:
  bot_token: '{{ k8s("default/slack-secrets/bot_token") }}'
```

### AWS payloads and nested fields

An AWS secret payload must be a JSON object (binary secrets are not supported). The field part is a dot-path, so nested keys are addressed with `.`:

```text theme={null}
secret payload: {"port": 5432, "cred": {"user": "analytics"}}

{{ aws('prod/db/port') }}        -> "5432"
{{ aws('prod/db/cred.user') }}   -> "analytics"
```

The resolved value must be a scalar (string, number, or boolean); pointing at a nested object raises an error. Referencing the same secret several times in one config triggers a single backend call, the payload is cached for the duration of the load.

The `aws` and `k8s` resolvers require optional dependencies: install `nao-core[aws-secrets]` or `nao-core[k8s-secrets]`. Unlike `env`, which resolves missing variables to an empty string and warns, `aws` and `k8s` raise a clear error at load time when a secret or field cannot be resolved.

## Top-level properties

| Property       | Type                             | Required | Default | Description                                                                                                         |
| -------------- | -------------------------------- | -------- | ------- | ------------------------------------------------------------------------------------------------------------------- |
| `project_name` | string                           | **Yes**  | —       | The name of the nao project                                                                                         |
| `threads`      | integer                          | No       | `1`     | Number of worker threads used by `nao sync`. Override per run with `nao sync -t/--threads`. Must be `1` or greater. |
| `databases`    | [DatabaseConfig\[\]](#databases) | No       | `[]`    | The databases to use                                                                                                |
| `repos`        | [RepoConfig\[\]](#repos)         | No       | `[]`    | The repositories to use                                                                                             |
| `notion`       | [NotionConfig](#notion)          | No       | `null`  | The Notion configurations                                                                                           |
| `llm`          | [LLMConfig](#llm)                | No       | `null`  | The LLM configuration                                                                                               |
| `slack`        | [SlackConfig](#slack)            | No       | `null`  | The Slack configuration                                                                                             |
| `mcp`          | [McpConfig](#mcp)                | No       | `null`  | The MCP configuration                                                                                               |
| `skills`       | [SkillsConfig](#skills)          | No       | `null`  | The Skills configuration                                                                                            |
| `test`         | [TestConfig](#test)              | No       | `null`  | The defaults used by `nao test`                                                                                     |

## Databases

All database configurations share these common fields:

| Property                         | Type               | Required | Default                                   | Description                                                                                                                                                                                                                                                                                                          |
| -------------------------------- | ------------------ | -------- | ----------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `type`                           | string — see below | **Yes**  | —                                         | —                                                                                                                                                                                                                                                                                                                    |
| `name`                           | string             | **Yes**  | —                                         | A friendly name for this connection                                                                                                                                                                                                                                                                                  |
| `include`                        | string\[]          | No       | `[]`                                      | Glob patterns for schemas/tables to include (e.g., 'prod\_*.*', 'analytics.dim\_\*'). Empty means include all.                                                                                                                                                                                                       |
| `exclude`                        | string\[]          | No       | `[]`                                      | Glob patterns for schemas/tables to exclude (e.g., 'temp\_*.*', '*.backup\_*')                                                                                                                                                                                                                                       |
| `exclude_columns`                | string\[]          | No       | `[]`                                      | Glob patterns matched against the fully-qualified `schema.table.column` name. Matching columns are dropped from everything the agent sees (column lists, previews, profiling). Useful for hiding replication metadata or internal columns (e.g., `'*._peerdb_*'`, `'*.version'`). Empty means no columns are hidden. |
| `templates`                      | string\[]          | No       | `["columns", "query_history", "preview"]` | Which default templates to render per table (e.g., \['columns', 'query\_history', 'profiling', 'ai\_summary']). Defaults to \['columns', 'query\_history', 'preview']. The legacy key `accessors` is still accepted.                                                                                                 |
| `query_history_days`             | integer            | No       | `0`                                       | Number of days of query history to fetch for the `query_history` template. Set to 0 to disable.                                                                                                                                                                                                                      |
| `query_history_sql`              | string             | No       | `null`                                    | Custom SQL to override the built-in query history fetch. Must return a `query_text` column. Use `{days}` as a placeholder for `query_history_days`.                                                                                                                                                                  |
| `query_history_exclude_patterns` | string\[]          | No       | `[]`                                      | Case-insensitive regex patterns. Queries matching any pattern are excluded from the `query_history` analysis.                                                                                                                                                                                                        |

**Template values:** `columns`, `preview`, `query_history`, `profiling`, `ai_summary`

Patterns in `include` / `exclude` use glob syntax against `schema.table` (e.g. `prod_*.*`, `analytics.dim_*`).

### PostgreSQL (`type: postgres`)

| Property      | Type    | Required | Default | Description                                         |
| ------------- | ------- | -------- | ------- | --------------------------------------------------- |
| `host`        | string  | **Yes**  | —       | PostgreSQL host                                     |
| `port`        | integer | No       | `5432`  | PostgreSQL port                                     |
| `database`    | string  | **Yes**  | —       | Database name                                       |
| `user`        | string  | **Yes**  | —       | Username                                            |
| `password`    | string  | **Yes**  | —       | Password                                            |
| `schema_name` | string  | No       | `null`  | Default schema (optional, uses 'public' if not set) |

### Snowflake (`type: snowflake`)

| Property           | Type                                                                     | Required | Default | Description                                              |
| ------------------ | ------------------------------------------------------------------------ | -------- | ------- | -------------------------------------------------------- |
| `username`         | string                                                                   | **Yes**  | —       | Snowflake username                                       |
| `account_id`       | string                                                                   | **Yes**  | —       | Snowflake account identifier (e.g., 'xy12345.us-east-1') |
| `password`         | string                                                                   | No       | `null`  | Snowflake password                                       |
| `database`         | string                                                                   | **Yes**  | —       | Snowflake database                                       |
| `schema_name`      | string                                                                   | No       | `null`  | Snowflake schema (optional)                              |
| `warehouse`        | string                                                                   | No       | `null`  | Snowflake warehouse to use (optional)                    |
| `private_key_path` | string                                                                   | No       | `null`  | Path to private key file for key-pair authentication     |
| `passphrase`       | string                                                                   | No       | `null`  | Passphrase for the private key if it is encrypted        |
| `authenticator`    | `"externalbrowser"`, `"username_password_mfa"`, `"jwt_token"`, `"oauth"` | No       | `null`  | Authentication method (e.g., 'externalbrowser' for SSO)  |

### BigQuery (`type: bigquery`)

| Property           | Type    | Required | Default | Description                                                                                                        |
| ------------------ | ------- | -------- | ------- | ------------------------------------------------------------------------------------------------------------------ |
| `project_id`       | string  | **Yes**  | —       | GCP project ID                                                                                                     |
| `dataset_id`       | string  | No       | `null`  | Default BigQuery dataset                                                                                           |
| `credentials_path` | string  | No       | `null`  | Path to service account JSON file. If not provided, uses Application Default Credentials (ADC)                     |
| `credentials_json` | object  | No       | `null`  | Service account credentials as a dict or JSON string. Takes precedence over credentials\_path if both are provided |
| `sso`              | boolean | No       | `false` | Use Single Sign-On (SSO) for authentication                                                                        |
| `location`         | string  | No       | `null`  | BigQuery location                                                                                                  |

### DuckDB (`type: duckdb`)

| Property | Type   | Required | Default      | Description                      |
| -------- | ------ | -------- | ------------ | -------------------------------- |
| `path`   | string | No       | `":memory:"` | Path to the DuckDB database file |

### Databricks (`type: databricks`)

| Property          | Type   | Required | Default | Description                                                                                                                                                                                      |
| ----------------- | ------ | -------- | ------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `server_hostname` | string | **Yes**  | —       | Databricks server hostname (e.g., 'adb-xxxx.azuredatabricks.net')                                                                                                                                |
| `http_path`       | string | **Yes**  | —       | HTTP path to the SQL warehouse or cluster                                                                                                                                                        |
| `access_token`    | string | **Yes**  | —       | Databricks personal access token                                                                                                                                                                 |
| `catalog`         | string | No       | `null`  | Unity Catalog name (optional)                                                                                                                                                                    |
| `schema_name`     | string | No       | `null`  | Default schema (optional)                                                                                                                                                                        |
| `temp_schema`     | string | No       | `null`  | A schema you have write access to, used for temporary storage during queries. Set this when `schema_name` is read-only. When set, it is used as the connection schema in place of `schema_name`. |

### Microsoft SQL Server (`type: mssql`)

| Property      | Type    | Required | Default     | Description                                                                  |
| ------------- | ------- | -------- | ----------- | ---------------------------------------------------------------------------- |
| `host`        | string  | **Yes**  | —           | MSSQL host                                                                   |
| `port`        | integer | No       | `1433`      | MSSQL port                                                                   |
| `database`    | string  | **Yes**  | —           | Database name                                                                |
| `user`        | string  | **Yes**  | —           | Username                                                                     |
| `password`    | string  | **Yes**  | —           | Password                                                                     |
| `driver`      | string  | No       | `"FreeTDS"` | ODBC driver (FreeTDS on Mac/Linux, ODBC Driver 18 for SQL Server on Windows) |
| `schema_name` | string  | No       | `null`      | Default schema (optional, uses 'dbo' if not set)                             |

### Amazon Redshift (`type: redshift`)

| Property      | Type                                                | Required | Default     | Description                                         |
| ------------- | --------------------------------------------------- | -------- | ----------- | --------------------------------------------------- |
| `host`        | string                                              | **Yes**  | —           | Redshift cluster endpoint                           |
| `port`        | integer                                             | No       | `5439`      | Redshift port                                       |
| `database`    | string                                              | **Yes**  | —           | Database name                                       |
| `user`        | string                                              | **Yes**  | —           | Username                                            |
| `password`    | string                                              | **Yes**  | —           | Password                                            |
| `schema_name` | string                                              | No       | `null`      | Default schema (optional, uses 'public' if not set) |
| `sslmode`     | string                                              | No       | `"require"` | SSL mode for the connection                         |
| `ssh_tunnel`  | [RedshiftSSHTunnelConfig](#redshiftsshtunnelconfig) | No       | `null`      | SSH tunnel configuration (optional)                 |

### StarRocks (`type: starrocks`)

| Property   | Type      | Required | Default | Description                                      |
| ---------- | --------- | -------- | ------- | ------------------------------------------------ |
| `host`     | string    | **Yes**  | -       | StarRocks FE host                                |
| `port`     | integer   | No       | `9030`  | StarRocks FE query port                          |
| `database` | string    | **Yes**  | -       | Database name                                    |
| `user`     | string    | **Yes**  | -       | Username                                         |
| `password` | string    | **Yes**  | -       | Password                                         |
| `catalogs` | string\[] | No       | `[]`    | List of catalogs to sync (multi-catalog support) |

### Trino (`type: trino`)

| Property         | Type                | Required | Default  | Description                                                                                                                                                                              |
| ---------------- | ------------------- | -------- | -------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `host`           | string              | **Yes**  | —        | Trino coordinator host                                                                                                                                                                   |
| `port`           | integer             | No       | `8080`   | Trino coordinator port (use `8443` for HTTPS)                                                                                                                                            |
| `catalog`        | string              | **Yes**  | —        | Catalog name                                                                                                                                                                             |
| `user`           | string              | **Yes**  | —        | Username                                                                                                                                                                                 |
| `schema_name`    | string              | No       | `null`   | Default schema (optional)                                                                                                                                                                |
| `password`       | string              | No       | `null`   | Password (optional). Requires `http_scheme: https`.                                                                                                                                      |
| `http_scheme`    | `"http"`, `"https"` | No       | `"http"` | Connection scheme. Set to `https` for TLS-only coordinators (Starburst, Stackable, OPA-authorized OSS Trino). Required for password auth.                                                |
| `verify`         | boolean or string   | No       | `true`   | TLS certificate verification when `http_scheme: https`. `true` uses system CAs, `false` disables verification, or pass a path to a CA bundle for an internal CA. Ignored on `http`.      |
| `jwt_token`      | string              | No       | `null`   | Bearer JWT for Trino's OAuth2/JWT authenticator. Takes precedence over `password` and forces `http_scheme: https`.                                                                       |
| `jwt_token_file` | string              | No       | `null`   | Path to a file holding the bearer JWT. Read on every connection, so an external refresher can rotate short-lived tokens without rewriting the config. Takes precedence over `jwt_token`. |

### ClickHouse (`type: clickhouse`)

| Property               | Type                 | Required | Default  | Description                                                                                                                       |
| ---------------------- | -------------------- | -------- | -------- | --------------------------------------------------------------------------------------------------------------------------------- |
| `host`                 | string               | **Yes**  | -        | ClickHouse server host                                                                                                            |
| `protocol`             | `"http"`, `"native"` | No       | `"http"` | Wire protocol. `http` uses the HTTP interface, `native` uses the TCP protocol for instances that do not expose HTTP.              |
| `port`                 | integer              | No       | `null`   | Server port. Defaults to 8123 (HTTP) / 8443 (HTTPS) for `protocol: http`, and 9000 (TCP) / 9440 (TCP+TLS) for `protocol: native`. |
| `database`             | string               | **Yes**  | -        | Database name                                                                                                                     |
| `user`                 | string               | **Yes**  | -        | Username                                                                                                                          |
| `password`             | string               | No       | `""`     | Password                                                                                                                          |
| `secure`               | boolean              | No       | `false`  | Use HTTPS for `protocol: http`, or TLS over TCP for `protocol: native`.                                                           |
| `verify`               | boolean              | No       | `true`   | Verify TLS certificates when using `protocol: native` with `secure: true`.                                                        |
| `connect_timeout`      | integer              | No       | `null`   | Connection timeout in seconds, passed to the underlying ClickHouse client.                                                        |
| `send_receive_timeout` | integer              | No       | `null`   | Send/receive timeout in seconds, passed to the underlying ClickHouse client.                                                      |

Unlike other database types, ClickHouse renders all available templates by default rather than the shared default set. System databases (`system`, `information_schema`, `INFORMATION_SCHEMA`) are skipped unless explicitly listed in `include`.

### Amazon Athena (`type: athena`)

| Property                | Type   | Required | Default     | Description                            |
| ----------------------- | ------ | -------- | ----------- | -------------------------------------- |
| `s3_staging_dir`        | string | **Yes**  | —           | S3 staging directory for query results |
| `region_name`           | string | **Yes**  | —           | AWS region name                        |
| `aws_access_key_id`     | string | No       | `null`      | AWS access key ID                      |
| `aws_secret_access_key` | string | No       | `null`      | AWS secret access key                  |
| `aws_session_token`     | string | No       | `null`      | AWS session token                      |
| `profile_name`          | string | No       | `null`      | AWS profile name                       |
| `schema_name`           | string | No       | `null`      | Athena schema name                     |
| `work_group`            | string | No       | `"primary"` | Athena workgroup                       |

### RedshiftSSHTunnelConfig

Nested under `ssh_tunnel` in a Redshift database entry.

| Property                     | Type    | Required | Default | Description                           |
| ---------------------------- | ------- | -------- | ------- | ------------------------------------- |
| `ssh_host`                   | string  | **Yes**  | —       | SSH host                              |
| `ssh_port`                   | integer | No       | `22`    | SSH port                              |
| `ssh_username`               | string  | **Yes**  | —       | SSH username                          |
| `ssh_private_key_path`       | string  | **Yes**  | —       | Path to SSH private key file          |
| `ssh_private_key_passphrase` | string  | No       | `null`  | SSH private key passphrase (optional) |

## LLM

| Property           | Type                                 | Required | Default | Description                                                                |
| ------------------ | ------------------------------------ | -------- | ------- | -------------------------------------------------------------------------- |
| `providers`        | [ProviderConfig](#providerconfig)\[] | No       | `[]`    | The LLM providers to use                                                   |
| `annotation_model` | string                               | No       | `null`  | Model to use for ai\_summary generation via prompt(...) in Jinja templates |
| `meta`             | object                               | No       | `null`  | Deprecated: declare costs on the matching model instead                    |

Declaring the provider inline (`llm.provider`, `llm.api_key`, ...) still works but is deprecated. Run `nao migrate` to rewrite an existing file into the `llm.providers` shape.

### ProviderConfig

One entry per provider under `llm.providers`.

| Property               | Type                                                                                                    | Required | Default | Description                                               |
| ---------------------- | ------------------------------------------------------------------------------------------------------- | -------- | ------- | --------------------------------------------------------- |
| `provider`             | `"openai"`, `"anthropic"`, `"mistral"`, `"gemini"`, `"openrouter"`, `"ollama"`, `"bedrock"`, `"vertex"` | **Yes**  | —       | The LLM provider to use                                   |
| `api_key`              | string                                                                                                  | No       | `null`  | The API key to use                                        |
| `base_url`             | string                                                                                                  | No       | `null`  | Optional custom base URL for the provider API             |
| `access_key`           | string                                                                                                  | No       | `null`  | AWS access key (only for Bedrock)                         |
| `secret_key`           | string                                                                                                  | No       | `null`  | AWS secret key (only for Bedrock)                         |
| `aws_region`           | string                                                                                                  | No       | `null`  | AWS region (only for Bedrock)                             |
| `aws_profile`          | string                                                                                                  | No       | `null`  | AWS CLI profile name (only for Bedrock, e.g. SSO profile) |
| `gcp_project`          | string                                                                                                  | No       | `null`  | GCP project ID (only for Vertex)                          |
| `gcp_location`         | string                                                                                                  | No       | `null`  | GCP location (only for Vertex)                            |
| `service_account_json` | string                                                                                                  | No       | `null`  | Service account JSON (only for Vertex)                    |
| `key_file`             | string                                                                                                  | No       | `null`  | Path to service account key file (only for Vertex)        |
| `models`               | [ModelConfig](#modelconfig)\[]                                                                          | No       | `[]`    | The models to expose for this provider, in display order  |

### ModelConfig

One entry per model under `llm.providers[].models`. Leave `models` empty to expose the provider's built-in models.

| Property   | Type                      | Required | Default | Description                                                                |
| ---------- | ------------------------- | -------- | ------- | -------------------------------------------------------------------------- |
| `id`       | string                    | **Yes**  | —       | The model identifier used by the provider                                  |
| `name`     | string                    | No       | `null`  | Display name shown in the model picker                                     |
| `default`  | boolean                   | No       | `false` | Preselect this model for new chats                                         |
| `costs`    | [ModelCosts](#modelcosts) | No       | `null`  | Price in US dollars per million tokens                                     |
| `settings` | object                    | No       | `null`  | Inference parameters for this model, e.g. temperature or reasoning\_effort |

### ModelCosts

Nested under `costs` in a model entry. Prices are in US dollars per million tokens.

| Property            | Type   | Required | Default | Description                              |
| ------------------- | ------ | -------- | ------- | ---------------------------------------- |
| `input_no_cache`    | number | No       | `null`  | Price of an uncached input token         |
| `input_cache_read`  | number | No       | `null`  | Price of an input token read from cache  |
| `input_cache_write` | number | No       | `null`  | Price of an input token written to cache |
| `output`            | number | No       | `null`  | Price of an output token                 |

### Provider authentication

| Provider     | Env variable                         | API key  | Base URL env          |
| ------------ | ------------------------------------ | -------- | --------------------- |
| `openai`     | `OPENAI_API_KEY`                     | required | `OPENAI_BASE_URL`     |
| `anthropic`  | `ANTHROPIC_API_KEY`                  | required | `ANTHROPIC_BASE_URL`  |
| `mistral`    | `MISTRAL_API_KEY`                    | required | `MISTRAL_BASE_URL`    |
| `gemini`     | `GEMINI_API_KEY`                     | required | `GEMINI_BASE_URL`     |
| `openrouter` | `OPENROUTER_API_KEY`                 | required | `OPENROUTER_BASE_URL` |
| `ollama`     | `OLLAMA_API_KEY`                     | none     | `OLLAMA_BASE_URL`     |
| `bedrock`    | `AWS_BEARER_TOKEN_BEDROCK`           | optional | —                     |
| `vertex`     | `VERTEX_GOOGLE_SERVICE_ACCOUNT_JSON` | none     | —                     |

### Default annotation models

Used for `ai_summary` generation when `annotation_model` is not set.

| Provider     | Default model                               |
| ------------ | ------------------------------------------- |
| `openai`     | `gpt-4.1-mini`                              |
| `anthropic`  | `claude-3-5-sonnet-latest`                  |
| `mistral`    | `mistral-small-latest`                      |
| `gemini`     | `gemini-2.0-flash`                          |
| `openrouter` | `openai/gpt-4.1-mini`                       |
| `ollama`     | `llama3.2`                                  |
| `bedrock`    | `anthropic.claude-3-5-sonnet-20241022-v2:0` |
| `vertex`     | `gemini-2.5-flash`                          |

## Repos

| Property     | Type      | Required | Default | Description                                                                             |
| ------------ | --------- | -------- | ------- | --------------------------------------------------------------------------------------- |
| `name`       | string    | **Yes**  | -       | The name of the repository                                                              |
| `url`        | string    | No       | `null`  | The URL of the Git repository to clone                                                  |
| `branch`     | string    | No       | `null`  | The branch to check out. Only valid with `url`.                                         |
| `local_path` | string    | No       | `null`  | Local filesystem path, relative to `nao_config.yaml` or absolute                        |
| `include`    | string\[] | No       | `[]`    | Glob patterns for files to include (e.g. `'models/**/*.sql'`). Empty means include all. |
| `exclude`    | string\[] | No       | `[]`    | Glob patterns for files to exclude (e.g. `'*.pyc'`)                                     |

Set exactly one of `url` or `local_path`: supplying both, or neither, fails validation. `branch` cannot be combined with `local_path`.

`include` and `exclude` are applied to both source types. For a `url` repository the full repo is cloned first, then non-matching files are dropped, so the globs control what ends up in your context rather than what is fetched.

## Notion

| Property  | Type      | Required | Default | Description        |
| --------- | --------- | -------- | ------- | ------------------ |
| `api_key` | string    | **Yes**  | —       | The API key to use |
| `pages`   | string\[] | **Yes**  | —       | The pages to sync  |

## Slack

| Property           | Type   | Required | Default                                    | Description                               |
| ------------------ | ------ | -------- | ------------------------------------------ | ----------------------------------------- |
| `bot_token`        | string | **Yes**  | —                                          | The bot token to use                      |
| `signing_secret`   | string | **Yes**  | —                                          | The signing secret for verifying requests |
| `post_message_url` | string | No       | `"https://slack.com/api/chat.postMessage"` | The Slack API URL for posting messages    |

## MCP

| Property         | Type   | Required | Default | Description                             |
| ---------------- | ------ | -------- | ------- | --------------------------------------- |
| `json_file_path` | string | **Yes**  | —       | Path to the MCP JSON configuration file |

## Skills

| Property      | Type   | Required | Default | Description               |
| ------------- | ------ | -------- | ------- | ------------------------- |
| `folder_path` | string | **Yes**  | —       | Path to the skills folder |

## Test

Defaults for `nao test`. Every property is overridden by the matching command line flag.

| Property     | Type                                  | Required | Default              | Description                                                             |
| ------------ | ------------------------------------- | -------- | -------------------- | ----------------------------------------------------------------------- |
| `models`     | string\[]                             | No       | `["openai:gpt-4.1"]` | The models to run the tests against, in the format 'provider:model\_id' |
| `threads`    | integer                               | No       | `1`                  | Number of test runs to execute in parallel                              |
| `comparison` | [ComparisonConfig](#comparisonconfig) | No       | —                    | Tolerances used when comparing results to the expected data             |

### ComparisonConfig

Nested under `test.comparison`. Controls how results are compared to the expected data.

| Property   | Type    | Required | Default | Description                                               |
| ---------- | ------- | -------- | ------- | --------------------------------------------------------- |
| `rtol`     | number  | No       | `1e-05` | Relative tolerance used to compare numeric values         |
| `atol`     | number  | No       | `1e-08` | Absolute tolerance used to compare numeric values         |
| `decimals` | integer | No       | `2`     | Decimals kept when rounding float values before comparing |

## Example

```yaml theme={null}
project_name: my-project

databases:
  - type: postgres
    name: prod-db
    host: localhost
    port: 5432
    database: analytics
    user: ${{ env('DB_USER') }}
    password: ${{ env('DB_PASSWORD') }}
    include:
      - "public.*"
    exclude:
      - "public.tmp_*"
    exclude_columns:
      - "*._peerdb_*"
    templates:
      - columns
      - query_history
      - preview
      - ai_summary

  - type: duckdb
    name: local
    path: ./warehouse.duckdb

repos:
  - name: dbt-models
    url: https://github.com/myorg/dbt-models.git
    branch: main

llm:
  annotation_model: gpt-4.1-mini
  providers:
    - provider: openai
      api_key: ${{ env('OPENAI_API_KEY') }}
      models:
        - id: gpt-4.1
          default: true
        - id: gpt-4.1-mini
          name: GPT-4.1 mini
          costs: # US dollars per million tokens
            input_no_cache: 0.4
            input_cache_read: 0.1
            output: 1.6
    - provider: anthropic
      api_key: ${{ env('ANTHROPIC_API_KEY') }}
      models:
        - id: claude-sonnet-4-5
          settings:
            temperature: 0

notion:
  api_key: ${{ env('NOTION_API_KEY') }}
  pages:
    - https://notion.so/my-page-id

slack:
  bot_token: ${{ env('SLACK_BOT_TOKEN') }}
  signing_secret: ${{ env('SLACK_SIGNING_SECRET') }}

mcp:
  json_file_path: ./agent/mcps/mcp.json

skills:
  folder_path: ./agent/skills/

test:
  models:
    - openai:gpt-4.1
    - anthropic:claude-sonnet-4-5
  threads: 4
  comparison:
    rtol: 0.00001
    atol: 0.00000001
    decimals: 2
```

## JSON Schema

The raw JSON Schema is available at [`config-schema.json`](https://github.com/getnao/nao-docs/blob/main/public/config-schema.json).
