Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
26 commits
Select commit Hold shift + click to select a range
47b4d8e
Add support for Dynatrace backend
Sidhi-03 Dec 6, 2025
b432021
Update .env.example
Sidhi-03 Dec 6, 2025
52fb4ae
Add dynatrace to HealthCheckResponse backend literal
Sidhi-03 Dec 6, 2025
b928954
Merge branch 'opentelementry/dynatracebackend' of github.com:Sidhi-03…
Sidhi-03 Dec 6, 2025
7def592
Update src/opentelemetry_mcp/backends/dynatrace.py
Sidhi-03 Dec 6, 2025
5d03653
Update src/opentelemetry_mcp/backends/dynatrace.py
Sidhi-03 Dec 6, 2025
fe9f8a5
timezone info implicitly and is easier to read
Sidhi-03 Dec 6, 2025
7564072
changed code
Sidhi-03 Dec 6, 2025
05fe5b2
Update src/opentelemetry_mcp/backends/dynatrace.py
Sidhi-03 Dec 6, 2025
211ca61
line 426 updated
Sidhi-03 Dec 6, 2025
de7a6aa
Merge branch 'opentelementry/dynatracebackend' of github.com:Sidhi-03…
Sidhi-03 Dec 6, 2025
4b972d8
Updated dynatrace
Sidhi-03 Dec 6, 2025
1bd9c81
Update src/opentelemetry_mcp/backends/dynatrace.py
Sidhi-03 Dec 6, 2025
5810d15
Updated dynatrac spacinge
Sidhi-03 Dec 6, 2025
4056c5e
Merge branch 'opentelementry/dynatracebackend' of github.com:Sidhi-03…
Sidhi-03 Dec 6, 2025
f6b82c8
Fix syntax errors and improve async trace fetching in Dynatrace backend
Sidhi-03 Dec 7, 2025
0b54f12
Replaced utc with UTC
Sidhi-03 Dec 9, 2025
6aa7308
Endpoint and errors fixed
Sidhi-03 Dec 16, 2025
7dd7765
Update src/opentelemetry_mcp/backends/dynatrace.py
Sidhi-03 Dec 16, 2025
12fe0ae
Update src/opentelemetry_mcp/backends/dynatrace.py
Sidhi-03 Dec 16, 2025
9526880
Update src/opentelemetry_mcp/backends/dynatrace.py
Sidhi-03 Dec 16, 2025
03ab5a4
Fixed DQL query
Sidhi-03 Dec 16, 2025
c3deb74
Merge branch 'opentelementry/dynatracebackend' of github.com:Sidhi-03…
Sidhi-03 Dec 16, 2025
e26bb70
Fixed critical DQL
Sidhi-03 Dec 16, 2025
e8277a4
Added Dynatrace integration tests
Sidhi-03 Dec 20, 2025
603098e
Added Dynatrace integration test
Sidhi-03 Dec 20, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .env.example
Original file line number Diff line number Diff line change
Expand Up @@ -24,3 +24,6 @@ LOG_LEVEL=INFO

# Optional: Maximum traces per query (default: 100, max: 1000)
MAX_TRACES_PER_QUERY=100
# Optional: Dynatrace specific configuration
BACKEND_TYPE=dynatrace
BACKEND_URL=https://abc12345.live.dynatrace.com
75 changes: 60 additions & 15 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -440,7 +440,7 @@ pip install opentelemetry-mcp

### Core Capabilities

- **🔌 Multiple Backend Support** - Connect to Jaeger, Grafana Tempo, or Traceloop
- **🔌 Multiple Backend Support** - Connect to Jaeger, Grafana Tempo, Traceloop, or Dynatrace
- **🤖 LLM-First Design** - Specialized tools for analyzing AI application traces
- **🔍 Advanced Filtering** - Generic filter system with powerful operators
- **📊 Token Analytics** - Track and aggregate LLM token usage across models and services
Expand All @@ -463,14 +463,14 @@ pip install opentelemetry-mcp

### Backend Support Matrix

| Feature | Jaeger | Tempo | Traceloop |
| ---------------- | :----: | :---: | :-------: |
| Search traces | ✓ | ✓ | ✓ |
| Advanced filters | ✓ | ✓ | ✓ |
| Span search | ✓\* | ✓ | ✓ |
| Token tracking | ✓ | ✓ | ✓ |
| Error traces | ✓ | ✓ | ✓ |
| LLM tools | ✓ | ✓ | ✓ |
| Feature | Jaeger | Tempo | Traceloop | Dynatrace |
| ---------------- | :----: | :---: | :-------: | :-------: |
| Search traces | ✓ | ✓ | ✓ | ✓ |
| Advanced filters | ✓ | ✓ | ✓ | ✓ |
| Span search | ✓\* | ✓ | ✓ | ✓ |
| Token tracking | ✓ | ✓ | ✓ | ✓ |
| Error traces | ✓ | ✓ | ✓ | ✓ |
| LLM tools | ✓ | ✓ | ✓ | ✓ |

<sub>\* Jaeger requires `service_name` parameter for span search</sub>

Expand All @@ -496,11 +496,12 @@ uv pip install -e ".[dev]"

### Supported Backends

| Backend | Type | URL Example | Notes |
| ------------- | ----------- | --------------------------- | -------------------------- |
| **Jaeger** | Local | `http://localhost:16686` | Popular open-source option |
| **Tempo** | Local/Cloud | `http://localhost:3200` | Grafana's trace backend |
| **Traceloop** | Cloud | `https://api.traceloop.com` | Requires API key |
| Backend | Type | URL Example | Notes |
| ------------- | ----------- | ---------------------------------------- | -------------------------- |
| **Jaeger** | Local | `http://localhost:16686` | Popular open-source option |
| **Tempo** | Local/Cloud | `http://localhost:3200` | Grafana's trace backend |
| **Traceloop** | Cloud | `https://api.traceloop.com` | Requires API key |
| **Dynatrace** | Cloud | `https://{env-id}.live.dynatrace.com` | Requires API token |

### Quick Configuration

Expand All @@ -525,7 +526,7 @@ opentelemetry-mcp --backend traceloop --url https://api.traceloop.com --api-key

| Variable | Type | Default | Description |
| ---------------------- | ------- | -------- | -------------------------------------------------- |
| `BACKEND_TYPE` | string | `jaeger` | Backend type: `jaeger`, `tempo`, or `traceloop` |
| `BACKEND_TYPE` | string | `jaeger` | Backend type: `jaeger`, `tempo`, `traceloop`, or `dynatrace` |
| `BACKEND_URL` | URL | - | Backend API endpoint (required) |
| `BACKEND_API_KEY` | string | - | API key (required for Traceloop) |
| `BACKEND_TIMEOUT` | integer | `30` | Request timeout in seconds |
Expand Down Expand Up @@ -581,6 +582,50 @@ BACKEND_API_KEY=your_api_key_here

> **Note:** The API key contains project information. The backend uses a project slug of `"default"` and Traceloop resolves the actual project/environment from the API key.

### Dynatrace

```bash
BACKEND_TYPE=dynatrace
BACKEND_URL=https://abc12345.live.dynatrace.com
BACKEND_API_KEY=dt0c01.ABC123...
```

**Configuration Details:**
- **BACKEND_URL**: Your Dynatrace environment URL (format: `https://{your-environment-id}.live.dynatrace.com`)
- **BACKEND_API_KEY**: Dynatrace API token with trace read permissions

**Creating a Dynatrace API Token:**
1. Log in to your Dynatrace environment
2. Go to **Settings** → **Integration** → **Dynatrace API**
3. Click **Generate new token**
4. Select scopes: **Read traces** (and optionally **Read entities** for service discovery)
5. Copy the token and use it as `BACKEND_API_KEY`

**Claude Desktop Integration Example:**

```json
{
"mcpServers": {
"opentelemetry-mcp": {
"command": "pipx",
"args": ["run", "opentelemetry-mcp"],
"env": {
"BACKEND_TYPE": "dynatrace",
"BACKEND_URL": "https://abc12345.live.dynatrace.com",
"BACKEND_API_KEY": "dt0c01.ABC123..."
}
}
}
}
```

**Troubleshooting Dynatrace Connection:**

- **401 Unauthorized**: Verify your API token has the correct permissions (Read traces scope)
- **404 Not Found**: Check that your BACKEND_URL is correct (should include environment ID)
- **Connection Timeout**: Ensure your network can reach the Dynatrace environment
- **No Traces Found**: Verify that OpenTelemetry traces are being sent to Dynatrace and check the time range of your queries

</details>

---
Expand Down
2 changes: 1 addition & 1 deletion src/opentelemetry_mcp/attributes.py
Original file line number Diff line number Diff line change
Expand Up @@ -161,7 +161,7 @@ class HealthCheckResponse(BaseModel):
"""Health check response from backend systems."""

status: Literal["healthy", "unhealthy"] = Field(..., description="Health status of the backend")
backend: Literal["jaeger", "tempo", "traceloop"] = Field(..., description="Backend type")
backend: Literal["jaeger", "tempo", "traceloop", "dynatrace"] = Field(..., description="Backend type")
url: str = Field(..., description="Backend URL")
error: str | None = Field(default=None, description="Error message if unhealthy")

Expand Down
Loading
Loading