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

# MCP servers

<Note>
  **Preview**

  This feature is in [Preview](/docs/astro/feature-previews).
</Note>

Astro provides experimental Model Context Protocol (MCP) servers that allow AI models and agents to securely access your Astro and Airflow resources. Connect to MCP servers natively or by using the `mcp-remote` module in compatible AI clients.

For enhanced agent capabilities such as Dag authoring, testing, and debugging, see the [Astronomer AI Agent tooling repository](https://github.com/astronomer/agents).

## MCP servers

Astro provides the following experimental MCP servers:

* **Astro Registry MCP server** (`astro-registry`) is a remote MCP server for accessing the Astro Registry.
* **Astro Cloud MCP server** (`astro-cloud`) is an authenticated remote MCP server for discovering and managing your Astro resources, including Deployments, Workspaces, and environment variables.

<Warning>
  **Astro Cloud MCP server deprecation**

  The current Astro Cloud MCP server (`astro-cloud`) is deprecated and shouldn't be used. An updated Astro MCP server is in progress and is slated for early access in July 2026. For more information, contact your Astronomer account executive.
</Warning>

## Set up the Astro Registry MCP server

<Tip>If you experience any issues, try restarting your client or disabling and re-enabling the Astro MCP server connection.</Tip>

<Tabs>
  <Tab title="Windsurf">
    1. Open Windsurf settings with `CTRL/CMD + ,`.

    2. Navigate to `Cascade` > `Manage plugins`.

    3. Select `View raw config`.

    4. Add the following configuration. Only include the `astro-cloud` section if you're using the authenticated Astro Cloud MCP server.

       ```json wrap theme={null}
       {
         "mcpServers": {
           "astro-registry": {
             "command": "npx",
             "args": [
               "-y",
               "mcp-remote",
               "https://api.astronomer.io/registryV2/v1alpha1/mcp"
             ]
           },
           "astro-cloud": {
             "command": "npx",
             "args": [
               "-y",
               "mcp-remote",
               "https://api.astronomer.io/v1alpha1/mcp?organizationId=<my-organization-id>",
               "--header",
               "Authorization: Bearer ${AUTH_TOKEN}"
             ],
             "env": {
               "AUTH_TOKEN": "<my-auth-token>"
             }
           }
         }
       }
       ```

    5. Click `Save` to save your configuration and check the `Plugins` section to verify that your server is connected.
  </Tab>

  <Tab title="Cursor">
    1. Open Cursor.

    2. Navigate to `Tools & Integrations` > `Add Custom MCP`.

    3. Add the following configuration. Only include the `astro-cloud` section if you're using the authenticated Astro Cloud MCP server.

       ```json wrap theme={null}
       {
         "mcpServers": {
           "astro-registry": {
             "url": "https://api.astronomer.io/registryV2/v1alpha1/mcp"
           },
           "astro-cloud": {
             "url": "https://api.astronomer.io/v1alpha1/mcp?organizationId=<my-organization-id>",
             "headers": {
               "Authorization":"Bearer <my-auth-token>"
             }
           }
         }
       }
       ```

    4. Save the configuration and check the `Tools & Integrations` > `MCP Servers` section to verify that your server is connected.
  </Tab>

  <Tab title="Claude Code">
    Claude Code connects to remote MCP servers natively without the `mcp-remote` module. You can configure the server at the project level (`.mcp.json`) or at the user level (`~/.claude.json`).

    The Astro Registry MCP server is public and requires no authentication. Run the following command to add it to your project:

    ```sh wrap theme={null}
    claude mcp add --transport http --scope project astro-registry \
      https://api.astronomer.io/registryV2/v1alpha1/mcp
    ```

    #### Add the Astro Cloud MCP server

    The Astro Cloud MCP server requires your Organization ID and an API token.

    <Steps>
      <Step title="Retrieve your Organization ID">
        If you have the Astro CLI installed and authenticated, run `astro organization list` to find your Organization ID. Otherwise, open the [Astro UI](https://cloud.astronomer.io/settings/general) and copy your Organization ID from **Settings** > **General**.
      </Step>

      <Step title="Create an API token">
        Create a [Workspace or Organization API token](/docs/astro/workspace-api-tokens) in the Astro UI.
      </Step>

      <Step title="Set the token as an environment variable">
        Add the following to your shell profile (`.zshrc`, `.bashrc`, or equivalent) so it persists across sessions:

        ```bash wrap theme={null}
        export ASTRO_AUTH_TOKEN=<your-token>
        ```
      </Step>

      <Step title="Add the server">
        Run the following command, replacing `<your-organization-id>` with the Organization ID you retrieved earlier:

        ```bash wrap theme={null}
        claude mcp add --transport http --scope project astro-cloud \
          "https://api.astronomer.io/v1alpha1/mcp?organizationId=<your-organization-id>" \
          --header "Authorization: Bearer ${ASTRO_AUTH_TOKEN}"
        ```
      </Step>

      <Step title="Verify the connection">
        Run `claude mcp list` and confirm both `astro-registry` and `astro-cloud` appear.
      </Step>
    </Steps>

    The resulting `.mcp.json` file should look similar to the following:

    ```json wrap theme={null}
    {
      "mcpServers": {
        "astro-registry": {
          "type": "http",
          "url": "https://api.astronomer.io/registryV2/v1alpha1/mcp"
        }
      }
    }
    ```
  </Tab>
</Tabs>

## Airflow MCP Plugin

The **Airflow MCP Plugin** ([`astro-airflow-mcp`](https://github.com/astronomer/agents/tree/main/astro-airflow-mcp)) is an open-source package that installs directly into an Airflow Deployment and exposes an MCP endpoint on the webserver. This gives AI tools direct access to Airflow's REST API — Dags, task logs, connections, variables, and more — without running a separate server.

Unlike the Astro Cloud MCP server (which manages Astro-level resources like Deployments and Workspaces), the Airflow MCP Plugin provides Airflow-level access for a single Deployment: listing Dags, viewing task logs, inspecting connections, diagnosing failures, and more.

The plugin auto-detects the installed Airflow version and registers the appropriate integration:

* **Airflow 3.x**: Mounts as a FastAPI app on the API server.
* **Airflow 2.x** (2.4 or later): Registers as a Flask blueprint on the webserver.

### Prerequisites

* An Airflow Deployment on Astro. The plugin supports Airflow 3.x (Runtime 3.1 or later) and Airflow 2.x (2.4 or later).
* A [Deployment API token](/docs/astro/deployment-api-tokens) with a role that allows POST requests (required by the MCP protocol). See [Configure authentication](#configure-authentication) for role options.

### Install the plugin

Add `astro-airflow-mcp` to your Astro project's `requirements.txt`:

```text wrap theme={null}
astro-airflow-mcp
```

Deploy the change. The package auto-registers as an Airflow plugin — no Dockerfile changes or additional configuration needed.

### Set environment variables

After deploying, set the following environment variable on your Deployment to block write operations:

```sh wrap theme={null}
astro deployment variable create \
  --deployment-id <deployment-id> \
  AF_READ_ONLY=true
```

| Variable       | Required    | Description                                                                                                                                                          |
| -------------- | ----------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `AF_READ_ONLY` | Recommended | Blocks all write operations (trigger, pause, clear, delete) at the MCP server level, regardless of the token's permissions. Set to `true` for safe read-only access. |

<Note>In plugin mode, the MCP server always runs in stateless HTTP mode, so Claude Code and other MCP clients work without additional configuration. The `FASTMCP_STATELESS_HTTP` environment variable applies only when running the MCP server as a standalone process.</Note>

### Configure authentication

The MCP protocol uses POST requests for all operations, including read-only ones. Your Deployment API token does **not** need write permissions for read-only MCP access: authorization is still based on the underlying Airflow permissions, so a custom role with read permissions such as `*.get` is sufficient. The important exception is `WORKSPACE_MEMBER`, which Astro's auth proxy blocks from making the POST requests the MCP protocol requires.

#### Option A: Use a built-in role

Create a [Deployment API token](/docs/astro/deployment-api-tokens) with one of the following roles:

* **DEPLOYMENT\_ADMIN** — Full access (works but overprivileged)
* **WORKSPACE\_OPERATOR** or **WORKSPACE\_AUTHOR** — Moderate privilege

<Warning>
  **WORKSPACE\_MEMBER** does not work with the MCP plugin. Astro's auth proxy blocks POST requests for this role, which prevents the MCP protocol handshake from completing.
</Warning>

#### Option B: Create a custom `MCP_VIEWER` role (recommended)

For least-privilege access, create a [custom Deployment role](/docs/astro/customize-deployment-roles) that includes only read permissions. This ensures the token can use all MCP read tools but cannot modify any Airflow resources.

1. In the Astro UI, go to **Settings**, then in the **Access Management** section, click **Roles & Permissions**, click **Custom**, then click **+ New Custom Role** (in the legacy UI, go to **Organization Settings** > **Access Management** > **Roles**, then click **+ Add Role**).

2. Set the **Scope** to **Deployment**.

3. Name the role `MCP_VIEWER` with a description like "Read-only access for Airflow MCP plugin."

4. Select all `deployment.airflow.*.get` permissions. See [Custom role permissions reference](/docs/astro/deployment-role-reference) for the full list. The role should include these 28 permissions:

   | Permission                               | Purpose                                    |
   | ---------------------------------------- | ------------------------------------------ |
   | `deployment.get`                         | Get Deployment information                 |
   | `deployment.airflow.adminMenu.get`       | View Admin menu (gates Airflow config API) |
   | `deployment.airflow.astronomer.get`      | View Astronomer menu                       |
   | `deployment.airflow.auditLog.get`        | View audit logs                            |
   | `deployment.airflow.browseMenu.get`      | View Browse menu                           |
   | `deployment.airflow.clusterActivity.get` | View cluster activity and DAG stats        |
   | `deployment.airflow.config.get`          | View Config menu                           |
   | `deployment.airflow.connection.get`      | View connections                           |
   | `deployment.airflow.customMenu.get`      | View custom plugin menus                   |
   | `deployment.airflow.dag.get`             | View Dags                                  |
   | `deployment.airflow.dagCode.get`         | View DAG source code                       |
   | `deployment.airflow.dagDependencies.get` | View DAG dependencies                      |
   | `deployment.airflow.dagRun.get`          | View DAG runs                              |
   | `deployment.airflow.datasets.get`        | View assets and datasets                   |
   | `deployment.airflow.docs.get`            | View documentation links                   |
   | `deployment.airflow.importError.get`     | View import errors                         |
   | `deployment.airflow.job.get`             | View scheduler jobs                        |
   | `deployment.airflow.plugin.get`          | View plugins                               |
   | `deployment.airflow.pool.get`            | View pools                                 |
   | `deployment.airflow.provider.get`        | View providers                             |
   | `deployment.airflow.slaMiss.get`         | View SLA misses                            |
   | `deployment.airflow.taskInstance.get`    | View task instances                        |
   | `deployment.airflow.taskLog.get`         | View task logs                             |
   | `deployment.airflow.taskReschedule.get`  | View task reschedules                      |
   | `deployment.airflow.trigger.get`         | View triggers                              |
   | `deployment.airflow.variable.get`        | View variables                             |
   | `deployment.airflow.website.get`         | Access the Airflow UI                      |
   | `deployment.airflow.xcom.get`            | View XCom data                             |

5. Click **Create role**.

Then create a Deployment API token with the new role:

```sh wrap theme={null}
astro deployment token create \
  --deployment-id <deployment-id> \
  --name "mcp-viewer" \
  --role MCP_VIEWER
```

### Connect your MCP client

After the plugin is deployed and a token is created, the MCP endpoint is available at:

```text wrap theme={null}
https://<deployment-webserver-url>/mcp/v1/
```

You can find your Deployment's webserver URL in the Astro UI on the Deployment's overview page.

<Tabs>
  <Tab title="Claude Code">
    ```sh wrap theme={null}
    claude mcp add -t http -s user \
      -H "Authorization: Bearer <token>" \
      -- airflow \
      "https://<deployment-webserver-url>/mcp/v1/"
    ```

    <Warning>
      Use `-t http`, not `-t sse`. The MCP endpoint returns SSE-formatted responses, but the correct Claude Code transport type is `http`. Using `-t sse` causes the connection to fail.
    </Warning>
  </Tab>

  <Tab title="Cursor">
    Add the following to your MCP configuration in Cursor (**Tools & Integrations** > **Add Custom MCP**):

    ```json wrap theme={null}
    {
      "mcpServers": {
        "airflow": {
          "url": "https://<deployment-webserver-url>/mcp/v1/",
          "headers": {
            "Authorization": "Bearer <token>"
          }
        }
      }
    }
    ```
  </Tab>

  <Tab title="VS Code / Other Clients">
    Add the following to your MCP client configuration file:

    ```json wrap theme={null}
    {
      "mcpServers": {
        "airflow": {
          "url": "https://<deployment-webserver-url>/mcp/v1/",
          "headers": {
            "Authorization": "Bearer <token>"
          }
        }
      }
    }
    ```
  </Tab>
</Tabs>

### Troubleshooting

| Symptom                                            | Cause                                                | Fix                                                                                                                                               |
| -------------------------------------------------- | ---------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------- |
| `Failed to connect` with `-t sse`                  | Wrong transport type                                 | Use `-t http` instead of `-t sse` in Claude Code                                                                                                  |
| 401 Unauthorized on MCP endpoint                   | Missing or expired token                             | Regenerate the Deployment API token                                                                                                               |
| 403 Forbidden on some read tools                   | Incomplete role permissions                          | Ensure the role includes all `deployment.airflow.*.get` permissions listed above                                                                  |
| 403 on `get_airflow_config` or `list_dag_warnings` | Airflow Admin RBAC required                          | A small number of Airflow API endpoints require the Admin role regardless of Astro permissions. Most MCP tools work without Admin access.         |
| `WORKSPACE_MEMBER` token fails                     | POST blocked by Astro auth proxy                     | Use a higher-privilege role or create a custom `MCP_VIEWER` role                                                                                  |
| 404 on MCP endpoint right after a deploy           | Plugin loads per-worker, rolling restart in progress | Wait for the rollout to settle, then retry. The first MCP call per worker also adds a small one-time latency while the FastMCP lifespan warms up. |
