Search

Integrate

How to Set Up the MCP Server: Claude Code, Cursor, Codex

How to set up the MAS MCP server in Claude Code, Cursor or Codex: connect Android, mint a token from an API key, and run a macro from chat.

  • Windows
  • Mac
  • Emulator
  • Cloud device
  • Phone
  • MCP
Intermediate Updated 8 min read
On this page
  1. Before you start
  2. The two surfaces: cloud devices and a local Android adb MCP server
  3. Get an MCP bearer token for the hosted server
  4. How to set up the MCP server in Claude Code, Cursor and Codex
  5. Try it
  6. Scopes
  7. Troubleshooting
  8. 401 or invalid token
  9. Token expired after an hour
  10. No devices listed
  11. Lease expired
  12. Next

This page shows how to set up the Macro Automation Studio (MAS) MCP server in Claude Code, Cursor, Codex, Claude Desktop and any other MCP client. The server turns your Android devices into tools an AI client can call. It has two surfaces: the hosted server, with 25 tools on your cloud devices, and the free local connector, with 13 tools on the emulator or phone on your desk.

Before you start

  • For the hosted server: a MAS account with at least one cloud device, and an API key created in the app. See API keys.
  • For the local connector: adb on your PATH, a running emulator with ADB switched on (or a phone with USB debugging), Python, and a checkout of the agent package. The app’s Integrations (MCP) page shows the exact command and working directory.
  • An MCP client that calls a remote server over streamable HTTP with a bearer header, or launches a stdio command.

The two surfaces: cloud devices and a local Android adb MCP server

Hosted serverLocal connector
How you reach itPOST https://api.automationmacro.com/mcppython -m masagent mcp on your machine
Tools25 tools: device control, vision, macros and runs, agent authoring, app maps13 tools: device control and vision
DevicesYour cloud devicesWhatever adb devices lists
AuthOne-hour bearer token minted from an API keyNone
Resourcesmas://docs/sdk-reference, mas://docs/house-libraryNone
CostCloud device time and AI credits are billed like the app; device tools carry no per-call chargeFree

Both surfaces speak JSON-RPC 2.0 at protocol version 2025-06-18: the hosted server over HTTPS on one stateless endpoint, one JSON reply per POST and no batch requests; the local connector over stdin and stdout, with no network calls of its own. Macro runs, agent authoring and app maps exist only on the hosted server. The full list is on the tools reference.

Get an MCP bearer token for the hosted server

The hosted server uses OAuth client credentials. Your API key is the client secret; you exchange it for a short-lived access token and send that token as a bearer header. There is no browser sign-in: no login page, no redirect, and no authorization-code flow.

  1. In MAS, open Integrations (MCP). Under Create an MCP credential, enter a name, tick the scopes you want and click Create credential & reveal key. The API Keys page creates the same kind of key with an expiry choice. Copy the key now; it starts with mas_ and is shown once.
  2. Exchange the key for a token. Put the key in MAS_API_KEY and run:
bash
curl -s -X POST https://api.automationmacro.com/api/mcp/oauth/token -d grant_type=client_credentials -d client_secret=$MAS_API_KEY
  1. Read access_token from the reply and store it in MAS_MCP_TOKEN. The reply also carries token_type (Bearer), expires_in (3600) and scope, which echoes the key’s scopes.
json
{"access_token":"eyJhbGciOi...","token_type":"Bearer","expires_in":3600,"scope":"devices:control,macros:run,maps:read"}

The endpoint also accepts a JSON body or HTTP Basic auth with the key as the password. A revoked, expired or unknown key answers 401 with invalid_client. Tokens live one hour; run the command again for a new one. Discovery documents sit under /.well-known on the same host.

How to set up the MCP server in Claude Code, Cursor and Codex

Each tab shows the hosted server first and the local connector second. Replace <your token> with your token, and point the local connector’s working directory at the agent package checkout, as the Integrations (MCP) page shows.

Add the hosted server with the token in your environment:

bash
claude mcp add --transport http mas https://api.automationmacro.com/mcp --header "Authorization: Bearer $MAS_MCP_TOKEN"

Add the local connector as a stdio server. Run this from a terminal opened in the agent package checkout so python -m masagent resolves:

bash
claude mcp add mas-local -- python -m masagent mcp

To pin the connector to one emulator, pass its adb serial: claude mcp add mas-local -e MAS_DEVICE=127.0.0.1:5555 -- python -m masagent mcp. Without it, the connector uses the first device adb lists.

Check the result with /mcp inside Claude Code, then ask it to list your devices and take a screenshot.

Cursor reads .cursor/mcp.json in your project, or ~/.cursor/mcp.json for every project. The hosted server is a remote entry with a header; the local connector is a command:

json
{
  "mcpServers": {
    "mas": {
      "url": "https://api.automationmacro.com/mcp",
      "headers": { "Authorization": "Bearer <your token>" }
    },
    "macro-automation-local": {
      "command": "python",
      "args": ["-m", "masagent", "mcp"],
      "cwd": "C:/path/to/macro-automation-agent"
    }
  }
}

When the token expires after an hour, mint a new one and update the file. Cursor’s MCP settings show both servers and their tools.

Codex CLI adds a streamable HTTP server with --url and reads the bearer token from an environment variable:

bash
codex mcp add mas --url https://api.automationmacro.com/mcp --bearer-token-env-var MAS_MCP_TOKEN

Add the local connector as a stdio command:

bash
codex mcp add mas-local -- python -m masagent mcp

Both land in ~/.codex/config.toml, where you can also set the connector’s working directory:

toml
[mcp_servers.mas]
url = "https://api.automationmacro.com/mcp"
bearer_token_env_var = "MAS_MCP_TOKEN"

[mcp_servers.mas-local]
command = "python"
args = ["-m", "masagent", "mcp"]
cwd = "C:/path/to/macro-automation-agent"

Export MAS_MCP_TOKEN before you start Codex. When the token expires, export a fresh one and restart.

Claude Desktop’s config file launches local commands, so the local connector goes in directly. Paste the block the Integrations (MCP) page gives you:

json
{
  "mcpServers": {
    "macro-automation-local": {
      "command": "python",
      "args": ["-m", "masagent", "mcp"],
      "cwd": "C:/path/to/macro-automation-agent"
    }
  }
}

Claude Desktop’s remote connectors expect an interactive sign-in, which the MAS server does not offer, so the hosted server needs a local bridge that adds the header. The bridge’s target is the same remote entry the other clients use:

json
{
  "mcpServers": {
    "mas": {
      "url": "https://api.automationmacro.com/mcp",
      "headers": { "Authorization": "Bearer <your token>" }
    }
  }
}

Restart Claude Desktop after editing the file.

Send JSON-RPC 2.0 requests as POST to https://api.automationmacro.com/mcp with Authorization: Bearer <your token> and Content-Type: application/json. Each POST gets one JSON body back. Call initialize, then tools/list, then tools/call; resources come from resources/list and resources/read.

bash
curl -s -X POST https://api.automationmacro.com/mcp \
  -H "Authorization: Bearer $MAS_MCP_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"jsonrpc":"2.0","id":1,"method":"tools/list"}'

Most clients take the standard mcpServers shape, with a remote entry for the hosted server and a command for the local connector:

json
{
  "mcpServers": {
    "mas": { "type": "http", "url": "https://api.automationmacro.com/mcp", "headers": { "Authorization": "Bearer <your token>" } },
    "mas-local": { "command": "python", "args": ["-m", "masagent", "mcp"] }
  }
}

The local connector needs no header; launch it from the agent checkout and pass --device <serial> or set MAS_DEVICE to choose the emulator.

Try it

Ask your client to list devices: list_devices returns your cloud devices with their state on the hosted server, or what adb sees on the local connector. Then ask for a screenshot; the image comes back as MCP image content the model looks at directly.

On the hosted server every device tool needs a lease. lease_device opens a control session on one cloud device and returns a lease_id; auto_start boots a stopped device first. A lease renews on every call, expires after 10 idle minutes, and does not lock the device against a second client. release_device ends it and the device keeps running. The typical loop is list_devices, lease_device, screenshot, tap or type_text, then release_device.

Running a saved macro through run_macro costs zero AI credits. author_macro starts a MAS Agent session and spends credits as it works; see MAS Agent.

Scopes

A key carries the scopes you tick when you create it; none ticked means full access. The hosted server checks the scope before every tool call and returns an error result when the token lacks it. The REST API ignores scopes.

ScopeTools it gates
devices:controlDevice control and vision: leases, screenshots, taps, typing, keys, apps, OCR and template matching
macros:runMacros and runs: list and read macros, start, check and stop runs
macros:authorAgent authoring: start, follow, answer and stop a session
maps:readApp maps: get_map
runs:readReserved; no tool requires it today

Troubleshooting

401 or invalid token

The endpoint answered {"error":"invalid_token"}: the Authorization header is missing, does not start with Bearer , carries the mas_ key instead of a token, or carries an expired token. Mint a token and send that. A revoked or expired key fails earlier, at the token endpoint, with invalid_client; create a new key in the app.

Token expired after an hour

Tokens live one hour and cannot be extended. Run the token command again. Codex reads the new value from the environment on restart; Cursor and Claude Desktop need it in the config file; Claude Code needs the server removed and re-added, because the shell expanded $MAS_MCP_TOKEN at add time.

No devices listed

On the hosted server, list_devices returns your cloud devices; an empty list means the account has none. Create one on the Cloud Devices page; see Cloud devices. A stopped device can still be leased with auto_start. On the local connector, the tool returns what adb devices lists: switch ADB on in the emulator, confirm adb devices shows it, and check that adb is on the PATH of the process that launched the connector. The error “no device: none connected and no ‘device’ argument or $MAS_DEVICE” means nothing was found and no serial was named.

Lease expired

A device tool answered “lease not found or expired”. More than 10 idle minutes passed since the last call, the lease belongs to a different key owner, or the server restarted and dropped its in-memory leases. Call lease_device again and use the new lease_id; nothing on the device is lost.

Next

The tools reference lists every tool with its parameters, surface and scope. API keys covers key expiry, revocation and limits. The MCP page has the overview and the FAQ.

Next steps

Related pages

Was this page helpful?

Questions? Ask in Discord