mcp-instana 0.1.1__tar.gz → 0.2.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- mcp_instana-0.2.0/.bob/mcp.json +3 -0
- mcp_instana-0.2.0/.github/workflows/ci.yml +127 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/CONTRIBUTING.md +39 -8
- mcp_instana-0.2.0/Dockerfile +60 -0
- mcp_instana-0.1.1/README.md → mcp_instana-0.2.0/PKG-INFO +473 -29
- mcp_instana-0.1.1/PKG-INFO → mcp_instana-0.2.0/README.md +450 -152
- mcp_instana-0.2.0/pyproject-runtime.toml +62 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/pyproject.toml +28 -106
- mcp_instana-0.2.0/src/application/application_analyze.py +628 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/application/application_catalog.py +3 -1
- mcp_instana-0.2.0/src/application/application_global_alert_config.py +653 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/application/application_metrics.py +6 -2
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/application/application_resources.py +3 -1
- mcp_instana-0.2.0/src/application/application_settings.py +1731 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/application/application_topology.py +6 -2
- mcp_instana-0.2.0/src/automation/action_catalog.py +416 -0
- mcp_instana-0.2.0/src/automation/action_history.py +338 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/core/server.py +159 -9
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/core/utils.py +2 -2
- mcp_instana-0.2.0/src/event/events_tools.py +850 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/infrastructure/infrastructure_analyze.py +7 -3
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/infrastructure/infrastructure_catalog.py +3 -1
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/infrastructure/infrastructure_metrics.py +6 -2
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/infrastructure/infrastructure_resources.py +7 -5
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/infrastructure/infrastructure_topology.py +5 -3
- mcp_instana-0.2.0/src/prompts/__init__.py +16 -0
- mcp_instana-0.2.0/src/prompts/application/__init__.py +1 -0
- mcp_instana-0.2.0/src/prompts/application/application_alerts.py +54 -0
- mcp_instana-0.2.0/src/prompts/application/application_catalog.py +26 -0
- mcp_instana-0.2.0/src/prompts/application/application_metrics.py +57 -0
- mcp_instana-0.2.0/src/prompts/application/application_resources.py +26 -0
- mcp_instana-0.2.0/src/prompts/application/application_settings.py +75 -0
- mcp_instana-0.2.0/src/prompts/application/application_topology.py +30 -0
- mcp_instana-0.2.0/src/prompts/events/__init__.py +1 -0
- mcp_instana-0.2.0/src/prompts/events/events_tools.py +161 -0
- mcp_instana-0.2.0/src/prompts/infrastructure/infrastructure_analyze.py +72 -0
- mcp_instana-0.2.0/src/prompts/infrastructure/infrastructure_catalog.py +53 -0
- mcp_instana-0.2.0/src/prompts/infrastructure/infrastructure_metrics.py +45 -0
- mcp_instana-0.2.0/src/prompts/infrastructure/infrastructure_resources.py +74 -0
- mcp_instana-0.2.0/src/prompts/infrastructure/infrastructure_topology.py +38 -0
- mcp_instana-0.2.0/src/prompts/settings/__init__.py +0 -0
- mcp_instana-0.2.0/src/prompts/settings/custom_dashboard.py +157 -0
- mcp_instana-0.2.0/src/prompts/website/__init__.py +1 -0
- mcp_instana-0.2.0/src/prompts/website/website_analyze.py +35 -0
- mcp_instana-0.2.0/src/prompts/website/website_catalog.py +40 -0
- mcp_instana-0.2.0/src/prompts/website/website_configuration.py +105 -0
- mcp_instana-0.2.0/src/prompts/website/website_metrics.py +34 -0
- mcp_instana-0.2.0/src/settings/__init__.py +1 -0
- mcp_instana-0.2.0/src/settings/custom_dashboard_tools.py +417 -0
- mcp_instana-0.2.0/src/website/__init__.py +0 -0
- mcp_instana-0.2.0/src/website/website_analyze.py +433 -0
- mcp_instana-0.2.0/src/website/website_catalog.py +171 -0
- mcp_instana-0.2.0/src/website/website_configuration.py +770 -0
- mcp_instana-0.2.0/src/website/website_metrics.py +241 -0
- mcp_instana-0.2.0/tests/application/test_application_analyze.py +425 -0
- mcp_instana-0.2.0/tests/application/test_application_global_alert_config.py +488 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/application/test_application_settings.py +1 -1
- mcp_instana-0.2.0/tests/automation/__init__.py +5 -0
- mcp_instana-0.2.0/tests/automation/test_action_catalog.py +346 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/core/test_server.py +212 -4
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/application/test_application_analyze.py +330 -373
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/application/test_application_catalog.py +23 -21
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/application/test_application_metrics.py +15 -19
- mcp_instana-0.2.0/tests/e2e/application/test_application_settings.py +1232 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/application/test_application_topology.py +2 -1
- mcp_instana-0.2.0/tests/e2e/event/test_events_tools.py +2755 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/infrastructure/test_infrastructure_metrics.py +14 -11
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/server/test_server_integration.py +15 -14
- mcp_instana-0.2.0/tests/event/test_events_tools.py +1455 -0
- mcp_instana-0.2.0/tests/prompts/__init__.py +1 -0
- mcp_instana-0.2.0/tests/prompts/application/__init__.py +2 -0
- mcp_instana-0.2.0/tests/prompts/application/test_application_alerts.py +41 -0
- mcp_instana-0.2.0/tests/prompts/application/test_application_catalog.py +26 -0
- mcp_instana-0.2.0/tests/prompts/application/test_application_metrics.py +36 -0
- mcp_instana-0.2.0/tests/prompts/application/test_application_resources.py +26 -0
- mcp_instana-0.2.0/tests/prompts/application/test_application_settings.py +56 -0
- mcp_instana-0.2.0/tests/prompts/application/test_application_topology.py +26 -0
- mcp_instana-0.2.0/tests/prompts/events/test_events_tools.py +53 -0
- mcp_instana-0.2.0/tests/prompts/infrastructure/__init__.py +2 -0
- mcp_instana-0.2.0/tests/prompts/infrastructure/test_infrastructure_analyze.py +38 -0
- mcp_instana-0.2.0/tests/prompts/infrastructure/test_infrastructure_catalog.py +43 -0
- mcp_instana-0.2.0/tests/prompts/infrastructure/test_infrastructure_metrics.py +28 -0
- mcp_instana-0.2.0/tests/prompts/infrastructure/test_infrastructure_resources.py +43 -0
- mcp_instana-0.2.0/tests/prompts/infrastructure/test_infrastructure_topology.py +33 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/run_all_tests.py +11 -2
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/run_all_tests_with_coverage.py +1 -1
- mcp_instana-0.2.0/uv.lock +1112 -0
- mcp_instana-0.1.1/.github/workflows/ci.yml +0 -37
- mcp_instana-0.1.1/src/application/application_analyze.py +0 -415
- mcp_instana-0.1.1/src/application/application_settings.py +0 -1135
- mcp_instana-0.1.1/src/event/events_tools.py +0 -523
- mcp_instana-0.1.1/src/prompts/mcp_prompts.py +0 -900
- mcp_instana-0.1.1/src/prompts/prompt_loader.py +0 -29
- mcp_instana-0.1.1/src/prompts/prompt_registry.json +0 -21
- mcp_instana-0.1.1/tests/application/test_application_analyze.py +0 -571
- mcp_instana-0.1.1/tests/e2e/event/test_events_tools.py +0 -742
- mcp_instana-0.1.1/tests/event/test_events_tools.py +0 -460
- mcp_instana-0.1.1/tests/prompts/__init__.py +0 -1
- mcp_instana-0.1.1/tests/prompts/test_mcp_prompts.py +0 -414
- mcp_instana-0.1.1/uv.lock +0 -3113
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/.github/dco.yml +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/.gitignore +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/LICENSE.md +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/images/architecture.png +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/images/call_tools.png +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/images/claudeResponse.png +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/images/claudeTools.png +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/images/copilot.png +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/images/copilotResponse.png +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/images/kubernetesEvents.png +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/images/mcpInstanaFlow.png +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/images/query_events.png +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/pyrightconfig.json +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/run_ruff_check.sh +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/application/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/application/application_alert_config.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/core/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/event/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/infrastructure/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/log/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/src/log/log_alert_configuration.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/README.md +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/application/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/application/test_application_alert_config.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/application/test_application_catalog.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/application/test_application_metrics.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/application/test_application_resources.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/application/test_application_topology.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/core/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/core/test_utils.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/README.md +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/application/test_application_alert_config.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/application/test_application_resources.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/conftest.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/infrastructure/test_infrastructure_analyze.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/infrastructure/test_infrastructure_catalog.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/infrastructure/test_infrastructure_resources.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/infrastructure/test_infrastructure_topology.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/pytest.ini +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/run_e2e_tests.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/e2e/utils/test_base_instana_client.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/event/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/infrastructure/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/infrastructure/test_infrastructure_analyze.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/infrastructure/test_infrastructure_catalog.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/infrastructure/test_infrastructure_metrics.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/infrastructure/test_infrastructure_resources.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/infrastructure/test_infrastructure_topology.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/log/__init__.py +0 -0
- {mcp_instana-0.1.1 → mcp_instana-0.2.0}/tests/log/test_log_alert_configuration.py +0 -0
|
@@ -0,0 +1,127 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
branches: [ main ]
|
|
6
|
+
pull_request:
|
|
7
|
+
branches: [ main, test-ci ]
|
|
8
|
+
|
|
9
|
+
jobs:
|
|
10
|
+
lint-and-test:
|
|
11
|
+
runs-on: ubuntu-latest
|
|
12
|
+
strategy:
|
|
13
|
+
matrix:
|
|
14
|
+
python-version: ['3.11']
|
|
15
|
+
|
|
16
|
+
steps:
|
|
17
|
+
- uses: actions/checkout@v4
|
|
18
|
+
|
|
19
|
+
- name: Set up Python ${{ matrix.python-version }}
|
|
20
|
+
uses: actions/setup-python@v5
|
|
21
|
+
with:
|
|
22
|
+
python-version: ${{ matrix.python-version }}
|
|
23
|
+
|
|
24
|
+
- name: Install uv
|
|
25
|
+
run: pip install uv
|
|
26
|
+
|
|
27
|
+
- name: Install dependencies
|
|
28
|
+
run: uv sync --all-extras
|
|
29
|
+
|
|
30
|
+
- name: Run ruff check
|
|
31
|
+
run: uv run ruff check .
|
|
32
|
+
|
|
33
|
+
- name: Run unit tests with verbose output
|
|
34
|
+
run: |
|
|
35
|
+
# Set environment variables to handle missing SDK modules gracefully
|
|
36
|
+
export PYTHONPATH=${{ github.workspace }}
|
|
37
|
+
export PYTHONUNBUFFERED="1"
|
|
38
|
+
export DISABLE_REAL_API_CALLS="true"
|
|
39
|
+
export CI="true"
|
|
40
|
+
|
|
41
|
+
# Run tests and filter out expected import errors
|
|
42
|
+
# Note: Some Instana SDK modules may not be available in CI environment
|
|
43
|
+
# but tests are designed to handle this gracefully
|
|
44
|
+
uv run test -v 2>&1 | sed '/Error importing Instana SDK/d' || true
|
|
45
|
+
|
|
46
|
+
- name: Run unit tests with coverage
|
|
47
|
+
run: |
|
|
48
|
+
# Set environment variables to handle missing SDK modules gracefully
|
|
49
|
+
export PYTHONPATH=${{ github.workspace }}
|
|
50
|
+
export PYTHONUNBUFFERED="1"
|
|
51
|
+
export DISABLE_REAL_API_CALLS="true"
|
|
52
|
+
export CI="true"
|
|
53
|
+
|
|
54
|
+
# Run tests with coverage and filter out expected import errors
|
|
55
|
+
# Note: Some Instana SDK modules may not be available in CI environment
|
|
56
|
+
# but tests are designed to handle this gracefully
|
|
57
|
+
uv run test-coverage 2>&1 | sed '/Error importing Instana SDK/d' || true
|
|
58
|
+
|
|
59
|
+
- name: Check environment for E2E tests
|
|
60
|
+
run: |
|
|
61
|
+
echo "Checking environment..."
|
|
62
|
+
pwd
|
|
63
|
+
ls -la
|
|
64
|
+
echo "Python version:"
|
|
65
|
+
python --version
|
|
66
|
+
echo "UV version:"
|
|
67
|
+
uv --version
|
|
68
|
+
echo "Checking test directories:"
|
|
69
|
+
ls -la tests/
|
|
70
|
+
ls -la tests/e2e/
|
|
71
|
+
echo "Checking source directories:"
|
|
72
|
+
ls -la src/
|
|
73
|
+
|
|
74
|
+
- name: Run E2E mocked tests
|
|
75
|
+
env:
|
|
76
|
+
INSTANA_API_TOKEN: "test_token"
|
|
77
|
+
INSTANA_BASE_URL: "https://test.instana.io"
|
|
78
|
+
PYTHONPATH: ${{ github.workspace }}
|
|
79
|
+
PYTHONUNBUFFERED: "1"
|
|
80
|
+
DISABLE_REAL_API_CALLS: "true"
|
|
81
|
+
CI: "true"
|
|
82
|
+
run: |
|
|
83
|
+
echo "Running E2E mocked tests..."
|
|
84
|
+
|
|
85
|
+
# Run E2E tests with mocked environment
|
|
86
|
+
uv run -m pytest tests/e2e/ -m "mocked" -v --tb=short --maxfail=10 || {
|
|
87
|
+
echo "E2E tests failed. Checking for specific errors..."
|
|
88
|
+
uv run -m pytest tests/e2e/ -m "mocked" -v --tb=long --maxfail=5
|
|
89
|
+
exit 1
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
- name: Run E2E tests with coverage
|
|
93
|
+
env:
|
|
94
|
+
INSTANA_API_TOKEN: "test_token"
|
|
95
|
+
INSTANA_BASE_URL: "https://test.instana.io"
|
|
96
|
+
PYTHONPATH: ${{ github.workspace }}
|
|
97
|
+
PYTHONUNBUFFERED: "1"
|
|
98
|
+
DISABLE_REAL_API_CALLS: "true"
|
|
99
|
+
CI: "true"
|
|
100
|
+
run: |
|
|
101
|
+
echo "Running E2E tests with coverage..."
|
|
102
|
+
|
|
103
|
+
# Run E2E tests with coverage
|
|
104
|
+
uv run -m pytest tests/e2e/ -m "mocked" --cov=src --cov-report=html --cov-report=term-missing -v --maxfail=10 || {
|
|
105
|
+
echo "E2E tests with coverage failed. Checking for specific errors..."
|
|
106
|
+
uv run -m pytest tests/e2e/ -m "mocked" -v --tb=long --maxfail=5
|
|
107
|
+
exit 1
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
- name: Upload coverage reports as artifacts
|
|
111
|
+
uses: actions/upload-artifact@v4
|
|
112
|
+
if: always()
|
|
113
|
+
with:
|
|
114
|
+
name: coverage-reports
|
|
115
|
+
path: |
|
|
116
|
+
htmlcov/
|
|
117
|
+
.coverage
|
|
118
|
+
retention-days: 30
|
|
119
|
+
|
|
120
|
+
- name: Upload coverage reports to Codecov
|
|
121
|
+
uses: codecov/codecov-action@v4
|
|
122
|
+
with:
|
|
123
|
+
file: ./htmlcov/coverage.xml
|
|
124
|
+
flags: unittests
|
|
125
|
+
name: codecov-umbrella
|
|
126
|
+
fail_ci_if_error: false
|
|
127
|
+
verbose: true
|
|
@@ -5,7 +5,8 @@
|
|
|
5
5
|
- [Contributing to MCP-Instana](#contributing-to-mcp-instana)
|
|
6
6
|
- [Prerequisites](#prerequisites)
|
|
7
7
|
- [Steps to Build a New MCP Tool](#steps-to-build-a-new-mcp-tool)
|
|
8
|
-
- [1.
|
|
8
|
+
- [1. Fork this repo](#1-fork-this-repo)
|
|
9
|
+
- [2. Set Up Your Development Environment](#2-set-up-your-development-environment)
|
|
9
10
|
- [3. Create a New MCP Tools Module](#3-create-a-new-mcp-tools-module)
|
|
10
11
|
- [4. Implement the MCP Tools class](#4-implement-the-mcp-tools-class)
|
|
11
12
|
- [5. Write API tool Description precisely](#5-write-api-tool-description-precisely)
|
|
@@ -32,23 +33,36 @@ This guide provides step-by-step instructions for building a new MCP (Model Cont
|
|
|
32
33
|
|
|
33
34
|
### Steps to Build a New MCP Tool
|
|
34
35
|
|
|
35
|
-
#### 1.
|
|
36
|
+
#### 1. Fork this repo
|
|
37
|
+
|
|
38
|
+
To begin development, you’ll need your own copy of the repository:
|
|
39
|
+
|
|
40
|
+
- Go to the GitHub page of this repository.
|
|
41
|
+
- Click the Fork button in the top-right corner.
|
|
42
|
+
- Select your personal GitHub account (or your organization’s account) as the destination.
|
|
43
|
+
- GitHub will create a forked copy of the repository under your account, e.g. https://github.com/<Your GitHub Username>/mcp-instana
|
|
44
|
+
|
|
45
|
+
#### 2. Set Up Your Development Environment
|
|
36
46
|
|
|
37
47
|
```bash
|
|
38
48
|
# Clone the repository
|
|
39
|
-
git clone https://github.com
|
|
49
|
+
git clone https://github.com/<Your GitHub Username>/mcp-instana.git
|
|
40
50
|
cd mcp-instana
|
|
41
51
|
|
|
42
52
|
# Set up the environment
|
|
43
53
|
uv sync
|
|
54
|
+
|
|
55
|
+
# Alternative: Install from PyPI
|
|
56
|
+
pip install mcp-instana
|
|
44
57
|
```
|
|
58
|
+
|
|
45
59
|
#### 3. Create a New MCP Tools Module
|
|
46
60
|
|
|
47
61
|
Create a new file in the src/client directory with a descriptive name following the pattern: <api_name>_mcp_tools.py
|
|
48
62
|
|
|
49
63
|
#### 4. Implement the MCP Tools class
|
|
50
64
|
|
|
51
|
-
Follow any existing tools class under src/
|
|
65
|
+
Follow any existing tools class under src/client to know the template structure for your new class.
|
|
52
66
|
|
|
53
67
|
#### 5. Write API tool Description precisely
|
|
54
68
|
|
|
@@ -81,20 +95,25 @@ async def get_example_data(self, query: str, ctx=None) -> Dict[str, Any]:
|
|
|
81
95
|
|
|
82
96
|
#### 6. Update the Main Server File
|
|
83
97
|
|
|
84
|
-
|
|
98
|
+
Update src/core/server.py to register your new tools:
|
|
85
99
|
|
|
86
100
|
#### 7. Test Your MCP Tool
|
|
87
101
|
|
|
88
|
-
|
|
102
|
+
Build the mcp-instana with:
|
|
89
103
|
|
|
90
104
|
```bash
|
|
105
|
+
# For development (editable install)
|
|
91
106
|
uv pip install -e .
|
|
107
|
+
|
|
108
|
+
# Or install from PyPI
|
|
109
|
+
pip install mcp-instana
|
|
92
110
|
```
|
|
93
111
|
|
|
94
|
-
Now open/restart the mcp host like
|
|
112
|
+
Now open/restart the mcp host like Claude Desktop/GitHub Copilot and then run the query to test your new tool.
|
|
95
113
|
|
|
96
|
-
To run the MCP server locally
|
|
114
|
+
To run the MCP server locally:
|
|
97
115
|
|
|
116
|
+
**Using Development Installation:**
|
|
98
117
|
```bash
|
|
99
118
|
# Run in Streamable HTTP mode
|
|
100
119
|
uv run src/core/server.py --transport streamable-http --debug
|
|
@@ -106,6 +125,18 @@ uv run src/core/server.py --tools app,infra --transport streamable-http
|
|
|
106
125
|
uv run src/core/server.py --list-tools
|
|
107
126
|
```
|
|
108
127
|
|
|
128
|
+
**Using CLI (PyPI Installation):**
|
|
129
|
+
```bash
|
|
130
|
+
# Run in Streamable HTTP mode
|
|
131
|
+
mcp-instana --transport streamable-http --debug
|
|
132
|
+
|
|
133
|
+
# Run with specific tool categories
|
|
134
|
+
mcp-instana --tools app,infra --transport streamable-http
|
|
135
|
+
|
|
136
|
+
# List all available tool categories
|
|
137
|
+
mcp-instana --list-tools
|
|
138
|
+
```
|
|
139
|
+
|
|
109
140
|
#### 8. Add Documentation
|
|
110
141
|
Update the README.md file to include your new tool in the tools table:
|
|
111
142
|
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
# Stage 1: Build stage with minimal runtime dependencies
|
|
2
|
+
FROM python:3.11-slim AS builder
|
|
3
|
+
|
|
4
|
+
# Install system dependencies needed for building
|
|
5
|
+
RUN apt-get update && apt-get install -y --no-install-recommends \
|
|
6
|
+
gcc \
|
|
7
|
+
g++ \
|
|
8
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
9
|
+
|
|
10
|
+
# Set working directory
|
|
11
|
+
WORKDIR /app
|
|
12
|
+
|
|
13
|
+
# Copy only the runtime dependency file and source code needed for the build
|
|
14
|
+
COPY pyproject-runtime.toml pyproject.toml
|
|
15
|
+
COPY src ./src
|
|
16
|
+
COPY README.md ./
|
|
17
|
+
|
|
18
|
+
# Install uv for dependency management
|
|
19
|
+
RUN pip install --no-cache-dir uv
|
|
20
|
+
|
|
21
|
+
# Install only runtime dependencies using the minimal pyproject-runtime.toml
|
|
22
|
+
RUN uv pip install --no-cache-dir --system .
|
|
23
|
+
|
|
24
|
+
# Stage 2: Runtime stage
|
|
25
|
+
FROM python:3.11-slim AS runtime
|
|
26
|
+
|
|
27
|
+
# Set working directory
|
|
28
|
+
WORKDIR /app
|
|
29
|
+
|
|
30
|
+
# Create a non-root user for security
|
|
31
|
+
RUN groupadd -r mcpuser && useradd -r -g mcpuser mcpuser
|
|
32
|
+
|
|
33
|
+
# Copy only the Python packages from builder (no source code needed)
|
|
34
|
+
COPY --from=builder /usr/local/lib/python3.11/site-packages /usr/local/lib/python3.11/site-packages
|
|
35
|
+
COPY --from=builder /usr/local/bin /usr/local/bin
|
|
36
|
+
|
|
37
|
+
# Copy only the source code needed for runtime
|
|
38
|
+
COPY src ./src
|
|
39
|
+
|
|
40
|
+
# Set ownership to non-root user
|
|
41
|
+
RUN chown -R mcpuser:mcpuser /app
|
|
42
|
+
|
|
43
|
+
# Switch to non-root user
|
|
44
|
+
USER mcpuser
|
|
45
|
+
|
|
46
|
+
# Expose the default port (configurable via PORT env var)
|
|
47
|
+
EXPOSE 8080
|
|
48
|
+
|
|
49
|
+
# Set environment variables (no hardcoded secrets)
|
|
50
|
+
ENV PYTHONPATH=/app
|
|
51
|
+
ENV PYTHONUNBUFFERED=1
|
|
52
|
+
ENV PORT=8080
|
|
53
|
+
|
|
54
|
+
# Health check using container's internal network
|
|
55
|
+
HEALTHCHECK --interval=30s --timeout=30s --start-period=5s --retries=3 \
|
|
56
|
+
CMD python -c "import requests; requests.get('http://127.0.0.1:8080/health', timeout=5)" || exit 1
|
|
57
|
+
|
|
58
|
+
# Run the server
|
|
59
|
+
ENTRYPOINT ["python", "-m", "src.core.server"]
|
|
60
|
+
CMD ["--transport", "streamable-http"]
|