go2rtc-mcp 0.1.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.
- go2rtc_mcp-0.1.0/PKG-INFO +397 -0
- go2rtc_mcp-0.1.0/README.md +379 -0
- go2rtc_mcp-0.1.0/pyproject.toml +55 -0
- go2rtc_mcp-0.1.0/pyproject.toml.orig +48 -0
- go2rtc_mcp-0.1.0/src/go2rtc_mcp/__init__.py +23 -0
- go2rtc_mcp-0.1.0/src/go2rtc_mcp/client.py +308 -0
- go2rtc_mcp-0.1.0/src/go2rtc_mcp/config.py +60 -0
- go2rtc_mcp-0.1.0/src/go2rtc_mcp/models.py +55 -0
- go2rtc_mcp-0.1.0/src/go2rtc_mcp/sanitizer.py +15 -0
- go2rtc_mcp-0.1.0/src/go2rtc_mcp/security.py +185 -0
- go2rtc_mcp-0.1.0/src/go2rtc_mcp/server.py +273 -0
|
@@ -0,0 +1,397 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: go2rtc-mcp
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Production-grade Model Context Protocol (MCP) server for go2rtc streaming servers
|
|
5
|
+
Author: Armen
|
|
6
|
+
Author-email: Armen <gaxkalik@gmail.com>
|
|
7
|
+
License-Expression: MIT
|
|
8
|
+
Requires-Dist: httpx>=0.28.1
|
|
9
|
+
Requires-Dist: mcp[cli]>=1.2.0
|
|
10
|
+
Requires-Dist: pydantic>=2.10.0
|
|
11
|
+
Requires-Dist: python-dotenv>=1.0.1
|
|
12
|
+
Requires-Dist: pyyaml>=6.0.2
|
|
13
|
+
Requires-Python: >=3.11
|
|
14
|
+
Project-URL: Homepage, https://github.com/gaxkalik/go2rtc-mcp
|
|
15
|
+
Project-URL: Repository, https://github.com/gaxkalik/go2rtc-mcp
|
|
16
|
+
Project-URL: Issues, https://github.com/gaxkalik/go2rtc-mcp/issues
|
|
17
|
+
Description-Content-Type: text/markdown
|
|
18
|
+
|
|
19
|
+
# go2rtc-mcp
|
|
20
|
+
|
|
21
|
+
A production-grade **Model Context Protocol (MCP)** server for [go2rtc](https://github.com/AlexxIT/go2rtc) (including Home Assistant's built-in `go2rtc` service). Designed primarily for **Linux** environments (Home Assistant Supervised/OS, Debian/Ubuntu, Docker, and headless media servers), `go2rtc-mcp` enables AI assistants and MCP clients to inspect camera streams, probe video/audio codecs, capture live JPEG snapshots, generate streaming playback URLs (WebRTC, MSE, HLS, MP4, MJPEG, RTSP), discover camera integrations, and manage streams dynamically—with **strict, automated credential redaction**.
|
|
22
|
+
|
|
23
|
+
---
|
|
24
|
+
|
|
25
|
+
## Table of Contents
|
|
26
|
+
|
|
27
|
+
- [Architecture & Security Guardrails](#architecture--security-guardrails)
|
|
28
|
+
- [Linux Installation & Quick Start](#linux-installation--quick-start)
|
|
29
|
+
- [Configuration](#configuration)
|
|
30
|
+
- [MCP Client Configuration (Linux, macOS, Windows)](#mcp-client-configuration-linux-macos-windows)
|
|
31
|
+
- [Running as a Systemd Service (Linux)](#running-as-a-systemd-service-linux)
|
|
32
|
+
- [Usage Guide](#usage-guide)
|
|
33
|
+
- [Example Natural-Language Prompts](#example-natural-language-prompts)
|
|
34
|
+
- [MCP Tools Reference & Examples](#mcp-tools-reference--examples)
|
|
35
|
+
- [MCP Resources Reference](#mcp-resources-reference)
|
|
36
|
+
- [MCP Prompts Reference](#mcp-prompts-reference)
|
|
37
|
+
- [Programmatic Python Usage](#programmatic-python-usage)
|
|
38
|
+
- [Project Structure](#project-structure)
|
|
39
|
+
- [Development & Testing](#development--testing)
|
|
40
|
+
- [License](#license)
|
|
41
|
+
|
|
42
|
+
---
|
|
43
|
+
|
|
44
|
+
## Architecture & Security Guardrails
|
|
45
|
+
|
|
46
|
+
Live `go2rtc` API endpoints (`/api/streams`, `/api/config`, `/api/hass`, `/api/log`) regularly return plaintext or URL-encoded camera credentials and authentication tokens in RTSP producer URLs. `go2rtc-mcp` enforces defense-in-depth security:
|
|
47
|
+
|
|
48
|
+
### 1. Centralized Recursive Credential Redaction (`redact_sensitive_data`)
|
|
49
|
+
Every MCP tool return value, MCP resource response, client error message, and log record passes through [`redact_sensitive_data`](src/go2rtc_mcp/security.py):
|
|
50
|
+
- **Universal URI Credential Masking**: Masks credentials in any URI scheme (`rtsp://`, `rtsps://`, `http://`, `https://`, `rtmp://`, `onvif://`, `dvrip://`, including chained prefixes like `ffmpeg:rtsp://...`).
|
|
51
|
+
- **Query Parameter Token Masking**: Masks sensitive query parameters (`token`, `access_token`, `auth`, `password`, `pass`, `pwd`, `secret`, `api_key`, `jwt`).
|
|
52
|
+
- **Recursive Dict Key & Value Sanitization**: Sanitizes both dictionary keys and values (crucial because `go2rtc` creates dynamic stream keys named after raw RTSP URLs), lists, tuples, sets, Pydantic models, and multiline YAML text.
|
|
53
|
+
- **Log Stream Redaction**: Attaches `RedactingLoggingFilter` to `httpx`, `httpcore`, `mcp`, and `go2rtc_mcp` loggers so credentials never reach `stdout`/`stderr` or `journald`.
|
|
54
|
+
|
|
55
|
+
**Example Transformation:**
|
|
56
|
+
```text
|
|
57
|
+
Raw from go2rtc:
|
|
58
|
+
rtsp://admin:mockpass%2A@192.0.2.10:554/Streaming/Channels/101
|
|
59
|
+
rtsp://stream.example.com/live?token=eyJmockToken123&tracks=v1a1
|
|
60
|
+
|
|
61
|
+
Returned by go2rtc-mcp:
|
|
62
|
+
rtsp://***:***@192.0.2.10:554/Streaming/Channels/101
|
|
63
|
+
rtsp://stream.example.com/live?token=***&tracks=v1a1
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
### 2. Command Execution Guardrail (`GO2RTC_ALLOW_EXEC_STREAMS`)
|
|
67
|
+
`go2rtc` allows stream sources starting with `exec:`, `echo:`, and `expr:` to execute host shell commands. By default (`GO2RTC_ALLOW_EXEC_STREAMS=false`), `go2rtc-mcp` rejects any `add_stream` or `update_stream` request containing `exec:`, `echo:`, or `expr:` (including chained forms like `ffmpeg:exec:...`) before any network request is issued.
|
|
68
|
+
|
|
69
|
+
---
|
|
70
|
+
|
|
71
|
+
## Linux Installation & Quick Start
|
|
72
|
+
|
|
73
|
+
### Prerequisites
|
|
74
|
+
- **Linux** (Debian, Ubuntu, Alpine, Arch, Fedora, Raspberry Pi OS, etc.)
|
|
75
|
+
- **Python** `>= 3.11`
|
|
76
|
+
- **[uv](https://docs.astral.sh/uv/)** package manager (recommended: `curl -LsSf https://astral.sh/uv/install.sh | sh`)
|
|
77
|
+
- Access to your `go2rtc` instance (e.g. `http://localhost:1984` or local network IP)
|
|
78
|
+
|
|
79
|
+
### 1. Clone the Repository
|
|
80
|
+
```bash
|
|
81
|
+
git clone https://github.com/gaxkalik/go2rtc-mcp.git
|
|
82
|
+
cd go2rtc-mcp
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
### 2. Install Dependencies with `uv`
|
|
86
|
+
```bash
|
|
87
|
+
uv sync
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
### 3. Configure Environment Variables
|
|
91
|
+
Copy `.env.example` to `.env`:
|
|
92
|
+
```bash
|
|
93
|
+
cp .env.example .env
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
Edit `.env` using your preferred editor (`nano .env` or `vim .env`):
|
|
97
|
+
```env
|
|
98
|
+
GO2RTC_URL=http://localhost:1984
|
|
99
|
+
GO2RTC_USERNAME=
|
|
100
|
+
GO2RTC_PASSWORD=
|
|
101
|
+
GO2RTC_TIMEOUT=15.0
|
|
102
|
+
GO2RTC_ALLOW_EXEC_STREAMS=false
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
### 4. Run and Test the MCP Server
|
|
106
|
+
Run over `stdio` transport (standard for MCP clients):
|
|
107
|
+
```bash
|
|
108
|
+
uv run go2rtc-mcp
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
Or test interactively in your browser with the official MCP Inspector:
|
|
112
|
+
```bash
|
|
113
|
+
npx @modelcontextprotocol/inspector uv run go2rtc-mcp
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
---
|
|
117
|
+
|
|
118
|
+
## Configuration
|
|
119
|
+
|
|
120
|
+
`go2rtc-mcp` loads settings from environment variables (and automatically reads a local `.env` file if present):
|
|
121
|
+
|
|
122
|
+
| Environment Variable | Default | Description |
|
|
123
|
+
| :--- | :--- | :--- |
|
|
124
|
+
| `GO2RTC_URL` | `http://localhost:1984` | Base HTTP/HTTPS URL of your `go2rtc` server |
|
|
125
|
+
| `GO2RTC_USERNAME` | *(empty)* | Optional HTTP Basic Auth username |
|
|
126
|
+
| `GO2RTC_PASSWORD` | *(empty)* | Optional HTTP Basic Auth password |
|
|
127
|
+
| `GO2RTC_TIMEOUT` | `15.0` | Request timeout in seconds |
|
|
128
|
+
| `GO2RTC_ALLOW_EXEC_STREAMS` | `false` | Set to `true` only if you explicitly allow `exec:` / `echo:` / `expr:` sources |
|
|
129
|
+
|
|
130
|
+
---
|
|
131
|
+
|
|
132
|
+
## MCP Client Configuration (Linux, macOS, Windows)
|
|
133
|
+
|
|
134
|
+
### Linux (`~/.config/Claude/claude_desktop_config.json` or `~/.gemini/config/mcp_config.json`)
|
|
135
|
+
```json
|
|
136
|
+
{
|
|
137
|
+
"mcpServers": {
|
|
138
|
+
"go2rtc": {
|
|
139
|
+
"command": "uv",
|
|
140
|
+
"args": [
|
|
141
|
+
"--directory",
|
|
142
|
+
"/home/user/go2rtc-mcp",
|
|
143
|
+
"run",
|
|
144
|
+
"go2rtc-mcp"
|
|
145
|
+
],
|
|
146
|
+
"env": {
|
|
147
|
+
"GO2RTC_URL": "http://localhost:1984",
|
|
148
|
+
"GO2RTC_USERNAME": "",
|
|
149
|
+
"GO2RTC_PASSWORD": "",
|
|
150
|
+
"GO2RTC_TIMEOUT": "15.0",
|
|
151
|
+
"GO2RTC_ALLOW_EXEC_STREAMS": "false"
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
```
|
|
157
|
+
|
|
158
|
+
> **Note**: Adjust `/home/user/go2rtc-mcp` (or `/config/go2rtc-mcp` on Home Assistant) to your actual installation path. Ensure `uv` is in your system `PATH` (e.g. `/home/user/.cargo/bin/uv` or `/usr/local/bin/uv`).
|
|
159
|
+
|
|
160
|
+
### macOS (`~/Library/Application Support/Claude/claude_desktop_config.json`)
|
|
161
|
+
Replace the directory path with `/Users/username/go2rtc-mcp`.
|
|
162
|
+
|
|
163
|
+
### Windows (`%APPDATA%\Claude\claude_desktop_config.json`)
|
|
164
|
+
Replace the directory path with `C:/Users/username/go2rtc-mcp`.
|
|
165
|
+
|
|
166
|
+
---
|
|
167
|
+
|
|
168
|
+
## Running as a Systemd Service (Linux)
|
|
169
|
+
|
|
170
|
+
If you wish to run `go2rtc-mcp` as a persistent background daemon or manage it through Linux `systemctl`:
|
|
171
|
+
|
|
172
|
+
Create `/etc/systemd/system/go2rtc-mcp.service`:
|
|
173
|
+
```ini
|
|
174
|
+
[Unit]
|
|
175
|
+
Description=go2rtc Model Context Protocol Server
|
|
176
|
+
After=network.target
|
|
177
|
+
|
|
178
|
+
[Service]
|
|
179
|
+
Type=simple
|
|
180
|
+
User=user
|
|
181
|
+
WorkingDirectory=/home/user/go2rtc-mcp
|
|
182
|
+
EnvironmentFile=/home/user/go2rtc-mcp/.env
|
|
183
|
+
ExecStart=/home/user/.cargo/bin/uv run go2rtc-mcp
|
|
184
|
+
Restart=always
|
|
185
|
+
RestartSec=5
|
|
186
|
+
|
|
187
|
+
[Install]
|
|
188
|
+
WantedBy=multi-user.target
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
Enable and start the service:
|
|
192
|
+
```bash
|
|
193
|
+
sudo systemctl daemon-reload
|
|
194
|
+
sudo systemctl enable --now go2rtc-mcp
|
|
195
|
+
sudo systemctl status go2rtc-mcp
|
|
196
|
+
```
|
|
197
|
+
|
|
198
|
+
---
|
|
199
|
+
|
|
200
|
+
## Usage Guide
|
|
201
|
+
|
|
202
|
+
### Example Natural-Language Prompts
|
|
203
|
+
Ask your AI assistant:
|
|
204
|
+
- *"List all cameras configured on my go2rtc server."*
|
|
205
|
+
- *"Take a snapshot of `door_camera` and describe the current scene."*
|
|
206
|
+
- *"Perform a security patrol across all active cameras."*
|
|
207
|
+
- *"Probe `garage_camera` codecs, resolution, and RTSP protocol."*
|
|
208
|
+
- *"Generate WebRTC viewer, HLS (.m3u8), and RTSP playback links for `outside_camera`."*
|
|
209
|
+
- *"Check recent go2rtc logs for connection errors or offline feeds."*
|
|
210
|
+
|
|
211
|
+
---
|
|
212
|
+
|
|
213
|
+
### MCP Tools Reference & Examples
|
|
214
|
+
|
|
215
|
+
#### 1. `get_server_info()`
|
|
216
|
+
Fetches `go2rtc` version, revision, host, and RTSP port (`GET /api`).
|
|
217
|
+
- **Sample Output:**
|
|
218
|
+
```json
|
|
219
|
+
{
|
|
220
|
+
"config_path": "/config/go2rtc.yaml",
|
|
221
|
+
"host": "localhost:1984",
|
|
222
|
+
"revision": "b5948cf",
|
|
223
|
+
"rtsp": {
|
|
224
|
+
"default_query": "video&audio",
|
|
225
|
+
"listen": ":554"
|
|
226
|
+
},
|
|
227
|
+
"version": "1.9.14"
|
|
228
|
+
}
|
|
229
|
+
```
|
|
230
|
+
|
|
231
|
+
#### 2. `list_streams()`
|
|
232
|
+
Lists all configured and active streams (`GET /api/streams`) with credentials automatically masked.
|
|
233
|
+
- **Sample Output:**
|
|
234
|
+
```json
|
|
235
|
+
{
|
|
236
|
+
"door_camera": {
|
|
237
|
+
"producers": [
|
|
238
|
+
{
|
|
239
|
+
"url": "rtsp://***:***@192.0.2.10:554/Streaming/Channels/101"
|
|
240
|
+
}
|
|
241
|
+
],
|
|
242
|
+
"consumers": []
|
|
243
|
+
},
|
|
244
|
+
"garage_camera": {
|
|
245
|
+
"producers": [
|
|
246
|
+
{
|
|
247
|
+
"url": "rtsp://***:***@192.0.2.11:554/Streaming/Channels/101"
|
|
248
|
+
}
|
|
249
|
+
],
|
|
250
|
+
"consumers": []
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
```
|
|
254
|
+
|
|
255
|
+
#### 3. `get_stream_info(stream_name: str, probe: bool = False)`
|
|
256
|
+
Fetches producer and consumer state for a specific camera (`GET /api/streams?src=<stream_name>`). Pass `probe=True` to query live codecs and SDP.
|
|
257
|
+
|
|
258
|
+
#### 4. `probe_stream(stream_name: str)`
|
|
259
|
+
Actively queries `GET /api/streams?src=<stream_name>&video=all&audio=all` to inspect active codecs (H.264, H.265, AAC, PCMA, Opus), SDP tracks, protocol (`rtsp+tcp`), and byte counters.
|
|
260
|
+
|
|
261
|
+
#### 5. `get_stream_snapshot(stream_name: str, width: int | None = None, height: int | None = None)`
|
|
262
|
+
Captures a live JPEG frame from `stream_name` (`GET /api/frame.jpeg?src=<stream_name>`) and returns it as a native MCP `Image` (`image/jpeg`) for multimodal vision models.
|
|
263
|
+
|
|
264
|
+
#### 6. `get_stream_urls(stream_name: str)`
|
|
265
|
+
Generates ready-to-use streaming URLs for web, mobile, and NVR playback:
|
|
266
|
+
- **Sample Output:**
|
|
267
|
+
```json
|
|
268
|
+
{
|
|
269
|
+
"stream": "door_camera",
|
|
270
|
+
"webrtc_viewer": "http://localhost:1984/stream.html?src=door_camera&mode=webrtc",
|
|
271
|
+
"mse_viewer": "http://localhost:1984/stream.html?src=door_camera&mode=mse",
|
|
272
|
+
"websocket_url": "ws://localhost:1984/api/ws?src=door_camera",
|
|
273
|
+
"hls_m3u8": "http://localhost:1984/api/stream.m3u8?src=door_camera",
|
|
274
|
+
"mp4_stream": "http://localhost:1984/api/stream.mp4?src=door_camera",
|
|
275
|
+
"mjpeg_stream": "http://localhost:1984/api/stream.mjpeg?src=door_camera",
|
|
276
|
+
"snapshot_jpeg": "http://localhost:1984/api/frame.jpeg?src=door_camera",
|
|
277
|
+
"rtsp_url": "rtsp://localhost:554/door_camera"
|
|
278
|
+
}
|
|
279
|
+
```
|
|
280
|
+
|
|
281
|
+
#### 7. `add_stream(stream_name: str, source_url: str)`
|
|
282
|
+
Dynamically registers or updates a stream (`PUT /api/streams?name=<name>&src=<url>`), validating against `GO2RTC_ALLOW_EXEC_STREAMS`.
|
|
283
|
+
|
|
284
|
+
#### 8. `update_stream(stream_name: str, source_url: str)`
|
|
285
|
+
Dynamically updates an existing stream source (`PATCH /api/streams`).
|
|
286
|
+
|
|
287
|
+
#### 9. `delete_stream(stream_name: str)`
|
|
288
|
+
Removes a dynamically registered stream (`DELETE /api/streams?src=<name>`).
|
|
289
|
+
|
|
290
|
+
#### 10. `get_config()`
|
|
291
|
+
Retrieves sanitized `go2rtc.yaml` configuration (`GET /api/config`) with all secrets masked.
|
|
292
|
+
|
|
293
|
+
#### 11. `get_server_logs(limit: int = 50)`
|
|
294
|
+
Fetches recent `go2rtc` log entries (`GET /api/log`) with credentials redacted.
|
|
295
|
+
|
|
296
|
+
#### 12. `discover_sources(provider: str = "hass")`
|
|
297
|
+
Discovers stream sources from integrations (`hass`, `onvif`, `dvrip`, `homekit`, `roborock`, `webtorrent`).
|
|
298
|
+
|
|
299
|
+
---
|
|
300
|
+
|
|
301
|
+
### MCP Resources Reference
|
|
302
|
+
|
|
303
|
+
| Resource URI | MIME Type | Description |
|
|
304
|
+
| :--- | :--- | :--- |
|
|
305
|
+
| `go2rtc://server/info` | `application/json` | Server version, revision, host, and RTSP listener config |
|
|
306
|
+
| `go2rtc://streams` | `application/json` | Complete dictionary of streams with redacted producer URLs |
|
|
307
|
+
| `go2rtc://streams/{stream_name}` | `application/json` | Producer and consumer details for `{stream_name}` |
|
|
308
|
+
| `go2rtc://config` | `text/yaml` | Sanitized `go2rtc.yaml` configuration |
|
|
309
|
+
|
|
310
|
+
---
|
|
311
|
+
|
|
312
|
+
### MCP Prompts Reference
|
|
313
|
+
|
|
314
|
+
- **`snapshot_all`**: Captures live frames from all cameras and generates a multi-camera visual security summary.
|
|
315
|
+
- **`security_patrol`**: Full security assessment combining stream health, frame capture, and log error analysis.
|
|
316
|
+
- **`diagnose_stream(stream_name)`**: Guided step-by-step diagnostic workflow for troubleshooting a camera.
|
|
317
|
+
- **`camera_urls(stream_name)`**: Formats all direct streaming integration links.
|
|
318
|
+
- **`stream_health_check`**: System-wide health audit of all streams, codecs, and logs.
|
|
319
|
+
|
|
320
|
+
---
|
|
321
|
+
|
|
322
|
+
### Programmatic Python Usage
|
|
323
|
+
|
|
324
|
+
```python
|
|
325
|
+
import asyncio
|
|
326
|
+
from go2rtc_mcp import Go2RtcClient, Go2RtcSettings, redact_sensitive_data
|
|
327
|
+
|
|
328
|
+
|
|
329
|
+
async def main() -> None:
|
|
330
|
+
settings = Go2RtcSettings.from_env()
|
|
331
|
+
client = Go2RtcClient(settings=settings)
|
|
332
|
+
|
|
333
|
+
# 1. Fetch server metadata
|
|
334
|
+
info = await client.get_server_info()
|
|
335
|
+
print("Server version:", info.get("version"))
|
|
336
|
+
|
|
337
|
+
# 2. List streams (credentials automatically masked)
|
|
338
|
+
streams = await client.list_streams()
|
|
339
|
+
for name, data in streams.items():
|
|
340
|
+
print(f"Stream: {name} -> {data}")
|
|
341
|
+
|
|
342
|
+
# 3. Capture a live JPEG snapshot
|
|
343
|
+
jpeg_bytes = await client.get_snapshot("door_camera", width=1280)
|
|
344
|
+
with open("door_snapshot.jpg", "wb") as f:
|
|
345
|
+
f.write(jpeg_bytes)
|
|
346
|
+
print("Saved door_snapshot.jpg")
|
|
347
|
+
|
|
348
|
+
|
|
349
|
+
if __name__ == "__main__":
|
|
350
|
+
asyncio.run(main())
|
|
351
|
+
```
|
|
352
|
+
|
|
353
|
+
---
|
|
354
|
+
|
|
355
|
+
## Project Structure
|
|
356
|
+
|
|
357
|
+
```text
|
|
358
|
+
go2rtc-mcp/
|
|
359
|
+
├── .env.example # Safe template for environment variables
|
|
360
|
+
├── .gitignore # Excludes .env, snapshots (*.jpg/*.png/*.mp4), and live dumps
|
|
361
|
+
├── LICENSE # MIT License
|
|
362
|
+
├── pyproject.toml # Package metadata, dependencies, pytest & ruff config
|
|
363
|
+
├── README.md # Project documentation and Linux usage guide
|
|
364
|
+
├── src/
|
|
365
|
+
│ └── go2rtc_mcp/
|
|
366
|
+
│ ├── __init__.py # Public package exports
|
|
367
|
+
│ ├── client.py # Async httpx Go2RtcClient with automatic redaction
|
|
368
|
+
│ ├── config.py # Pydantic Go2RtcSettings & dotenv loader
|
|
369
|
+
│ ├── models.py # Pydantic models for server & stream objects
|
|
370
|
+
│ ├── sanitizer.py # Alias module re-exporting security redaction utilities
|
|
371
|
+
│ ├── security.py # redact_sensitive_data, validate_stream_source, log filter
|
|
372
|
+
│ └── server.py # MCPServer tools, resources, prompts, and CLI entry point
|
|
373
|
+
└── tests/
|
|
374
|
+
├── test_client.py # respx unit tests for Go2RtcClient endpoints & error handling
|
|
375
|
+
├── test_security.py # Unit tests for URI schemes, recursive redaction & exec policy
|
|
376
|
+
└── test_server.py # Unit tests for MCP tools, resources, snapshots & prompts
|
|
377
|
+
```
|
|
378
|
+
|
|
379
|
+
---
|
|
380
|
+
|
|
381
|
+
## Development & Testing
|
|
382
|
+
|
|
383
|
+
All unit tests use synthetic RFC 5737 (`192.0.2.0/24`) test fixtures and mock responses via `respx` so tests run offline and deterministically on Linux:
|
|
384
|
+
|
|
385
|
+
```bash
|
|
386
|
+
# Run unit tests
|
|
387
|
+
uv run python -m pytest -v
|
|
388
|
+
|
|
389
|
+
# Run ruff linter
|
|
390
|
+
uv run ruff check src/ tests/
|
|
391
|
+
```
|
|
392
|
+
|
|
393
|
+
---
|
|
394
|
+
|
|
395
|
+
## License
|
|
396
|
+
|
|
397
|
+
Released under the [MIT License](LICENSE).
|