# MCP server

Source: https://geondex.com/docs/mcp

> Install the Geondex MCP server in Claude Code, Cursor, VS Code, Windsurf, Codex or Claude Desktop and ask four AI engines about your site.



Your agent can already write GEO advice and read robots.txt. It cannot ask Perplexity, ChatGPT, Claude and Gemini the same question and compare who they cite, and it cannot remember last month. That is what this server adds.

## Install

Get a key on [your account page](/account). Every client sends it the same way: an `Authorization: Bearer gx_…` header on `https://geondex.com/mcp`. Replace `gx_YOUR_KEY` below with your key.

### Claude Code

Run once in your terminal:

```bash
claude mcp add --transport http geondex https://geondex.com/mcp --header "Authorization: Bearer gx_YOUR_KEY"
```

### Cursor

Add to `.cursor/mcp.json` in your project, or `~/.cursor/mcp.json` for every project:

```json
{
  "mcpServers": {
    "geondex": {
      "url": "https://geondex.com/mcp",
      "headers": { "Authorization": "Bearer gx_YOUR_KEY" }
    }
  }
}
```

### VS Code (GitHub Copilot agent mode)

Add to `.vscode/mcp.json`. VS Code asks for the key once and stores it securely, so it never sits in the file:

```json
{
  "inputs": [
    { "type": "promptString", "id": "geondex-key", "description": "Geondex API key", "password": true }
  ],
  "servers": {
    "geondex": {
      "type": "http",
      "url": "https://geondex.com/mcp",
      "headers": { "Authorization": "Bearer ${input:geondex-key}" }
    }
  }
}
```

### Windsurf

Open the MCP settings in Cascade, choose to view the raw config, and add this to `mcp_config.json`:

```json
{
  "mcpServers": {
    "geondex": {
      "serverUrl": "https://geondex.com/mcp",
      "headers": { "Authorization": "Bearer gx_YOUR_KEY" }
    }
  }
}
```

### OpenAI Codex CLI

Put your key in the `GEONDEX_API_KEY` environment variable, then run once. Codex reads the key from the variable, so it never sits in a config file:

```bash
codex mcp add geondex --url https://geondex.com/mcp --bearer-token-env-var GEONDEX_API_KEY
```

Or add it to `~/.codex/config.toml` by hand:

```toml
[mcp_servers.geondex]
url = "https://geondex.com/mcp"
bearer_token_env_var = "GEONDEX_API_KEY"
```

### Claude Desktop

Claude Desktop reaches remote servers through a small local bridge (needs Node.js). Settings → Developer → Edit Config, then add to `claude_desktop_config.json` and restart:

```json
{
  "mcpServers": {
    "geondex": {
      "command": "npx",
      "args": ["-y", "mcp-remote", "https://geondex.com/mcp", "--header", "Authorization: Bearer ${GEONDEX_API_KEY}"],
      "env": { "GEONDEX_API_KEY": "gx_YOUR_KEY" }
    }
  }
}
```

On Windows, spaces inside `"args"` can break. Use this form instead:

```json
"args": ["-y", "mcp-remote", "https://geondex.com/mcp", "--header", "Authorization:${GEONDEX_AUTH}"],
"env": { "GEONDEX_AUTH": "Bearer gx_YOUR_KEY" }
```

### Any other client, or raw HTTP

The endpoint speaks streamable HTTP and holds no session. Any client that can send a header works. For raw HTTP, your `accept` header must list **both** `application/json` and `text/event-stream`. Sending only one gets you a `406`.

```bash
curl -X POST https://geondex.com/mcp -H "Authorization: Bearer gx_YOUR_KEY" -H "content-type: application/json" -H "accept: application/json, text/event-stream" -d '{"jsonrpc":"2.0","id":1,"method":"tools/list"}'
```

## Tools

| Tool                                             | What it does                                                | Cost                    |
| ------------------------------------------------ | ----------------------------------------------------------- | ----------------------- |
| [`check_visibility`](/docs/api/check-visibility) | Ask four AI engines whether your domain is cited, right now | 3 credits / engine      |
| [`history`](/docs/api/history)                   | Your stored record of past checks for your domain           | Free                    |
| [`suggest_prompts`](/docs/api/suggest-prompts)   | Buyer-intent questions to check your domain against         | 1 credit                |
| [`check_crawlers`](/docs/api/check-crawlers)     | Whether robots.txt blocks the crawlers that cite you        | Free                    |
| [`audit_page`](/docs/api/audit-page)             | Grade one URL's structured data for AI citation             | 1 credit                |
| [`google_rank`](/docs/api/google-rank)           | Google position for a keyword, plus AI Overview presence    | 1 credit                |
| [`keyword_volume`](/docs/api/keyword-volume)     | Monthly search volume for up to 1,000 keywords              | 1 / 10 keywords, min 20 |

Response times: `check_visibility` up to 25 s; `suggest_prompts`, `audit_page`, `google_rank` and `keyword_volume` up to 10 s; `check_crawlers` up to 3 s; `history` up to 2 s. `keyword_volume` takes up to 1,000 keywords in one call, and up to 200 keywords cost the same 20 credits, so send them together.

Each tool name links to its REST reference: the arguments are the same, and so is the JSON that comes back.

## Three prompts to try

1. Check ttsensei.com for "best table tennis blade for beginners" on all four engines and tell me who is cited instead of me.
2. Suggest five buyer questions for aigregator.com, check each one, and list the engines where I am missing.
3. Re-run last week's checks for ttsensei.com and tell me what changed. Then look up Google rank for the ones where I lost a citation.

## What comes back

Every tool returns a one-line summary first, then the full JSON. Agents act on the line and read the JSON when they need detail:

```text
ttsensei.com cited by 1 of 4 engines that answered (openai #3). Not cited by perplexity, claude, gemini. Since 6 days ago: openai #5 → #3; claude dropped you.
```

`position` is a page's place in that engine's own citation list, so compare it over time for one engine rather than across two different engines.

Every field of every response is in the [API reference](/docs/api) — MCP returns the same JSON.

## Errors

A bad or missing key is refused before any tool runs: HTTP `401` with a JSON-RPC error whose `data.code` is `invalid_api_key`. Over 1,000 requests a day on one key gets HTTP `429`, `data.code` `rate_limited`, and a `Retry-After` header.

A tool that fails comes back as a normal tool result with `isError: true` and one line of text, `code: message`, using the same codes as the REST API. For example:

```text
credits_exhausted: This call needs 12 credits; you have 5. Your free plan gives 200 credits a month — upgrade or buy a pack at https://geondex.com/account.
```

A call that fails is not charged. The full list of codes is on [Errors & rate limits](/docs/errors).

## Limits

Every tool returns in under 25 seconds. An engine that does not answer within 20 seconds is reported as timed out and is not charged. Keys are limited to 1,000 requests a day. When credits run out you get a clear error with a link to upgrade or buy a pack; nothing is queued and nothing is charged automatically. Prices are on [/pricing](/pricing).

Prefer plain HTTP? The same seven calls are on the [REST API](/docs/api). Want your agent to know how to use them well? Add the [agent skills](/docs/mcp/skills).
