PyStreamMCP 3.3.1__tar.gz → 3.3.2__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.
- pystreammcp-3.3.2/PKG-INFO +266 -0
- pystreammcp-3.3.2/README.md +203 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/pyproject.toml +1 -1
- pystreammcp-3.3.2/python/PyStreamMCP.egg-info/PKG-INFO +266 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/__init__.py +1 -1
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/cli_daemon.py +14 -2
- pystreammcp-3.3.1/PKG-INFO +0 -404
- pystreammcp-3.3.1/README.md +0 -341
- pystreammcp-3.3.1/python/PyStreamMCP.egg-info/PKG-INFO +0 -404
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/LICENSE +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/MANIFEST.in +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/PyStreamMCP.egg-info/SOURCES.txt +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/PyStreamMCP.egg-info/dependency_links.txt +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/PyStreamMCP.egg-info/entry_points.txt +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/PyStreamMCP.egg-info/requires.txt +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/PyStreamMCP.egg-info/top_level.txt +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/_mcp_connector.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/_mcp_tools.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/adapters.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/agent.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/api.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/cli.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/cli_dashboard.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/context.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/decomposition.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/discovery.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/integrations/__init__.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/integrations/crewai.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/integrations/haystack.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/integrations/langchain.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/integrations/langsmith.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/integrations/llamaindex.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/integrations/pydantic_ai.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/integrations/semantic_kernel.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/mcp_server.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/ml/__init__.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/ml/relevance.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/ml/tagging.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/ml.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/multi_agent.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/observability/__init__.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/observability/metrics.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/okf_core.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/okf_discovery.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/okf_query_planner.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/optimization/__init__.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/optimization/advanced.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/optimization/decomposition.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/optimization.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/orchestration/__init__.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/orchestration/airflow.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/orchestration/nocode_rpa.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/orchestration/temporal.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/qa/__init__.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/qa/validator.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/quality.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/query.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/scripts/__init__.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/scripts/post_install.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/server.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/streaming.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/testing.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/webhook_handlers.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/python/pystreammcp/webhook_router.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/setup.cfg +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/setup.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_cli.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_discovery.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_integration_phase2.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_langchain_integration.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_llamaindex_integration.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_mcp_connector_discovery.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_mcp_server_resilience.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_mcp_tools_handler.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_okf_core.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_okf_discovery.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_okf_query_planner.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_phase3_advanced.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_phase3_items12.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_phase3_items345.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_sprint1_foundation.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_sprint2_langchain.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_sprint3_rag_frameworks.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_sprint4_agent_frameworks.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_sprint5_orchestration.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_statguardian_integration.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_webhook_hmac_auth.py +0 -0
- {pystreammcp-3.3.1 → pystreammcp-3.3.2}/tests/test_webhook_router.py +0 -0
|
@@ -0,0 +1,266 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: PyStreamMCP
|
|
3
|
+
Version: 3.3.2
|
|
4
|
+
Summary: Intelligent MCP orchestration hub - Intent understanding, capability matching, tool ranking with cohesive foundation
|
|
5
|
+
Author-email: Georgi Mammen Mullassery <mullassery@gmail.com>
|
|
6
|
+
License-Expression: Apache-2.0
|
|
7
|
+
Project-URL: Repository, https://github.com/Mullassery/PyStreamMCP
|
|
8
|
+
Project-URL: Issues, https://github.com/Mullassery/PyStreamMCP/issues
|
|
9
|
+
Classifier: Development Status :: 4 - Beta
|
|
10
|
+
Classifier: Intended Audience :: Developers
|
|
11
|
+
Classifier: Programming Language :: Python :: 3
|
|
12
|
+
Classifier: Programming Language :: Python :: 3.9
|
|
13
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
14
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
15
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
16
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
17
|
+
Requires-Python: >=3.9
|
|
18
|
+
Description-Content-Type: text/markdown
|
|
19
|
+
License-File: LICENSE
|
|
20
|
+
Requires-Dist: pydantic>=2.0
|
|
21
|
+
Requires-Dist: python-frontmatter>=1.0.0
|
|
22
|
+
Requires-Dist: click>=8.0
|
|
23
|
+
Requires-Dist: rich>=13.0
|
|
24
|
+
Requires-Dist: httpx>=0.24.0
|
|
25
|
+
Requires-Dist: toml>=0.10; python_version < "3.11"
|
|
26
|
+
Provides-Extra: dev
|
|
27
|
+
Requires-Dist: pytest>=7.0; extra == "dev"
|
|
28
|
+
Requires-Dist: pytest-cov>=4.0; extra == "dev"
|
|
29
|
+
Requires-Dist: pytest-asyncio>=0.21.0; extra == "dev"
|
|
30
|
+
Provides-Extra: api
|
|
31
|
+
Requires-Dist: fastapi>=0.104.0; extra == "api"
|
|
32
|
+
Requires-Dist: uvicorn[standard]>=0.24.0; extra == "api"
|
|
33
|
+
Requires-Dist: pydantic-settings>=2.0; extra == "api"
|
|
34
|
+
Requires-Dist: flask>=2.3.0; extra == "api"
|
|
35
|
+
Provides-Extra: mcp
|
|
36
|
+
Requires-Dist: mcp>=0.1.0; extra == "mcp"
|
|
37
|
+
Provides-Extra: langchain
|
|
38
|
+
Requires-Dist: langchain>=0.1.0; extra == "langchain"
|
|
39
|
+
Provides-Extra: llamaindex
|
|
40
|
+
Requires-Dist: llama-index>=0.9.0; extra == "llamaindex"
|
|
41
|
+
Provides-Extra: semantic-kernel
|
|
42
|
+
Requires-Dist: semantic-kernel>=0.4.0; extra == "semantic-kernel"
|
|
43
|
+
Provides-Extra: crewai
|
|
44
|
+
Requires-Dist: crewai>=0.1.0; extra == "crewai"
|
|
45
|
+
Provides-Extra: pydantic-ai
|
|
46
|
+
Requires-Dist: pydantic-ai>=0.1.0; extra == "pydantic-ai"
|
|
47
|
+
Provides-Extra: haystack
|
|
48
|
+
Requires-Dist: haystack-ai>=2.0.0; extra == "haystack"
|
|
49
|
+
Provides-Extra: temporal
|
|
50
|
+
Requires-Dist: temporalio>=1.0.0; extra == "temporal"
|
|
51
|
+
Provides-Extra: airflow
|
|
52
|
+
Requires-Dist: apache-airflow>=2.7.0; extra == "airflow"
|
|
53
|
+
Provides-Extra: all-integrations
|
|
54
|
+
Requires-Dist: langchain>=0.1.0; extra == "all-integrations"
|
|
55
|
+
Requires-Dist: llama-index>=0.9.0; extra == "all-integrations"
|
|
56
|
+
Requires-Dist: semantic-kernel>=0.4.0; extra == "all-integrations"
|
|
57
|
+
Requires-Dist: crewai>=0.1.0; extra == "all-integrations"
|
|
58
|
+
Requires-Dist: pydantic-ai>=0.1.0; extra == "all-integrations"
|
|
59
|
+
Requires-Dist: haystack-ai>=2.0.0; extra == "all-integrations"
|
|
60
|
+
Requires-Dist: temporalio>=1.0.0; extra == "all-integrations"
|
|
61
|
+
Requires-Dist: apache-airflow>=2.7.0; extra == "all-integrations"
|
|
62
|
+
Dynamic: license-file
|
|
63
|
+
|
|
64
|
+
# PyStreamMCP
|
|
65
|
+
|
|
66
|
+
[](https://pypi.org/project/pystreammcp/)
|
|
67
|
+
[](https://github.com/Mullassery/PyStreamMCP/actions/workflows/ci.yml)
|
|
68
|
+
[](https://www.python.org)
|
|
69
|
+
[](./LICENSE)
|
|
70
|
+
|
|
71
|
+
Context and token optimization for AI agents — query planning, source discovery, and MCP orchestration.
|
|
72
|
+
|
|
73
|
+
## What it is
|
|
74
|
+
|
|
75
|
+
PyStreamMCP is an AI-agent intelligence layer: query planning, context discovery, and
|
|
76
|
+
token-cost optimization, exposed both as a Python SDK and as an MCP (Model Context
|
|
77
|
+
Protocol) tool server. It also includes a small event-driven orchestration/federation
|
|
78
|
+
layer for coordinating multiple MCP endpoints. The published package is **pure Python** —
|
|
79
|
+
`pip install` works with no Rust toolchain or compiler.
|
|
80
|
+
|
|
81
|
+
## Features / Highlights
|
|
82
|
+
|
|
83
|
+
- **Agent query planning** — `pystreammcp.Agent` with selectable optimization strategies
|
|
84
|
+
(`token_efficient`, `balanced`, `quality_first`) and token accounting.
|
|
85
|
+
- **Source discovery** — `SourceRegistry` ranks registered data sources by real
|
|
86
|
+
word-overlap relevance (Jaccard) to a query; backs REST `/discover`, the
|
|
87
|
+
`pystreammcp_discover` MCP tool, and `LangchainAdapter.discover()`.
|
|
88
|
+
- **MCP tool server** — `PyStreamMCPHandler` wires the MCP tool-call surface directly to a
|
|
89
|
+
live `Orchestrator`/`EventRouter`; MCP tool args are validated with Pydantic and the
|
|
90
|
+
advertised schema is generated from the same models.
|
|
91
|
+
- **MCP orchestration & federation** — `Orchestrator` probes each configured endpoint's
|
|
92
|
+
real `tools/list` MCP method, with lexical tool-relevance ranking and capability
|
|
93
|
+
matching.
|
|
94
|
+
- **Webhook event server** — `pystreammcp.server.create_flask_app()` exposes an
|
|
95
|
+
HMAC-SHA256-signed event endpoint; unsigned or invalid events are rejected, and the
|
|
96
|
+
endpoint fails closed (`503`) if no secret is configured.
|
|
97
|
+
- **Framework adapters** — LangChain, LlamaIndex, CrewAI, Semantic Kernel, PydanticAI,
|
|
98
|
+
and Haystack under `pystreammcp.integrations`.
|
|
99
|
+
- **CLI** — `pystreammcp` with `query` / `server` / `version` / `dashboard`.
|
|
100
|
+
- **OKF integration** — an Open Knowledge Format catalog/discovery/query-planner feature
|
|
101
|
+
(see [`OKF_INTEGRATION.md`](OKF_INTEGRATION.md)).
|
|
102
|
+
|
|
103
|
+
## Who it's for / Use cases
|
|
104
|
+
|
|
105
|
+
- **Giving an AI agent a query-planning layer over multiple data sources**, exposed as
|
|
106
|
+
real MCP tools rather than hand-rolled per-agent glue code.
|
|
107
|
+
- **Coordinating multiple MCP endpoints** through the event-driven
|
|
108
|
+
orchestration/federation layer instead of wiring each one separately.
|
|
109
|
+
- **Tracking token-cost optimization** across agent queries.
|
|
110
|
+
- **Adding MCP support to an existing agent framework** through the shipped adapters.
|
|
111
|
+
|
|
112
|
+
## What it is not
|
|
113
|
+
|
|
114
|
+
- **The Rust backend is not shipped.** `core/` and `python/src/lib.rs` are an in-progress
|
|
115
|
+
Rust workspace intended as a future performance backend; the wheel built from
|
|
116
|
+
`pyproject.toml` is pure Python. The workspace compiles and its tests pass, but it is
|
|
117
|
+
tracked separately and not part of the published package.
|
|
118
|
+
- **Some orchestration capabilities are not fully implemented.** Cross-project federated
|
|
119
|
+
query *execution* and cross-database joins currently report
|
|
120
|
+
`"status": "not_implemented"` with an explanation, rather than fabricated result rows.
|
|
121
|
+
- **Source discovery is a word-overlap heuristic, not semantic search.**
|
|
122
|
+
`SourceRegistry` uses Jaccard token overlap; wrap it with your own similarity scoring if
|
|
123
|
+
you need embeddings.
|
|
124
|
+
- **Optional concurrency/framework packages have Python constraints.** The core SDK
|
|
125
|
+
(`Agent`, `SourceRegistry`, `Orchestrator`) supports Python 3.9+, but the `mcp` and
|
|
126
|
+
`semantic-kernel` extras require Python 3.10+ (their upstream packages don't publish
|
|
127
|
+
3.9-compatible releases). CI tests 3.10, 3.11, and 3.12 only.
|
|
128
|
+
- **Known dependency CVEs.** `pip-audit` (run 2026-09-20) found 7 known CVEs in
|
|
129
|
+
transitive dependencies (`werkzeug` via `flask`, `nltk` via `llama-index`). See
|
|
130
|
+
[`ROADMAP_HONEST.md`](ROADMAP_HONEST.md) §4.
|
|
131
|
+
- **The HTTP servers have no auth layer of their own.** They bind to `127.0.0.1`
|
|
132
|
+
(localhost-only) by default; pass `host="0.0.0.0"` explicitly only inside a network
|
|
133
|
+
boundary you control. The event endpoint requires HMAC-SHA256 signatures. See
|
|
134
|
+
[SECURITY.md](SECURITY.md).
|
|
135
|
+
|
|
136
|
+
## Project status
|
|
137
|
+
|
|
138
|
+
**Beta.** Current version **3.3.1** (`Development Status :: 4 - Beta`). The pure-Python
|
|
139
|
+
package is the shipped artifact and is under active hardening; the Rust workspace compiles
|
|
140
|
+
and passes its tests but is not shipped. The most recent pass fixed the Rust build,
|
|
141
|
+
Python `ruff` findings, and a stale integration test — see
|
|
142
|
+
[`ROADMAP_HONEST.md`](ROADMAP_HONEST.md) for the unhedged status.
|
|
143
|
+
|
|
144
|
+
## Installation
|
|
145
|
+
|
|
146
|
+
```bash
|
|
147
|
+
pip install PyStreamMCP
|
|
148
|
+
```
|
|
149
|
+
|
|
150
|
+
Optional extras — install only what you need:
|
|
151
|
+
|
|
152
|
+
```bash
|
|
153
|
+
pip install "PyStreamMCP[api]" # FastAPI + Flask HTTP servers
|
|
154
|
+
pip install "PyStreamMCP[mcp]" # MCP protocol client library
|
|
155
|
+
pip install "PyStreamMCP[langchain]" # LangChain adapter
|
|
156
|
+
pip install "PyStreamMCP[llamaindex]" # LlamaIndex adapter
|
|
157
|
+
pip install "PyStreamMCP[semantic-kernel]" # Semantic Kernel adapter
|
|
158
|
+
pip install "PyStreamMCP[all-integrations]" # every framework adapter
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
Requires Python 3.9+ for the core SDK; the `mcp` and `semantic-kernel` extras require
|
|
162
|
+
Python 3.10+.
|
|
163
|
+
|
|
164
|
+
## Quick start
|
|
165
|
+
|
|
166
|
+
```python
|
|
167
|
+
from pystreammcp import Agent
|
|
168
|
+
|
|
169
|
+
agent = Agent(
|
|
170
|
+
agent_id="recommendation_engine",
|
|
171
|
+
name="Product Recommendation Engine",
|
|
172
|
+
optimization_strategy="token_efficient", # or "balanced" / "quality_first"
|
|
173
|
+
max_tokens=1000,
|
|
174
|
+
)
|
|
175
|
+
|
|
176
|
+
result = agent.query("What are the top 10 customers by lifetime value?")
|
|
177
|
+
|
|
178
|
+
print(f"Baseline tokens: {result.baseline_tokens}")
|
|
179
|
+
print(f"Optimized tokens: {result.optimized_tokens}")
|
|
180
|
+
print(f"Reduction: {result.cost_reduction_percent:.1f}%")
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
Token counts are estimated from the actual query text (a ~4-characters-per-token
|
|
184
|
+
heuristic) and the reduction is computed from the selected strategy — not a fixed number.
|
|
185
|
+
See [`examples/basic_usage.py`](examples/basic_usage.py) for a full walkthrough.
|
|
186
|
+
|
|
187
|
+
## Usage
|
|
188
|
+
|
|
189
|
+
**Data source discovery:**
|
|
190
|
+
|
|
191
|
+
```python
|
|
192
|
+
from pystreammcp import SourceRegistry
|
|
193
|
+
|
|
194
|
+
registry = SourceRegistry()
|
|
195
|
+
registry.register(
|
|
196
|
+
"orders_db",
|
|
197
|
+
description="customer order history and revenue by quarter",
|
|
198
|
+
type="database",
|
|
199
|
+
tags=["orders", "revenue"],
|
|
200
|
+
)
|
|
201
|
+
|
|
202
|
+
results = registry.discover("customer revenue by quarter")
|
|
203
|
+
# [{"name": "orders_db", "type": "database", "relevance": 0.4444, "matched_terms": [...]}]
|
|
204
|
+
```
|
|
205
|
+
|
|
206
|
+
**MCP orchestration & federation** (`pystreammcp.toml`):
|
|
207
|
+
|
|
208
|
+
```toml
|
|
209
|
+
[federation]
|
|
210
|
+
endpoints = [
|
|
211
|
+
"http://localhost:8765/mcp",
|
|
212
|
+
"http://localhost:8766/mcp",
|
|
213
|
+
]
|
|
214
|
+
```
|
|
215
|
+
|
|
216
|
+
```python
|
|
217
|
+
from pystreammcp import Orchestrator
|
|
218
|
+
|
|
219
|
+
orch = Orchestrator() # reads ./pystreammcp.toml
|
|
220
|
+
result = orch.discover_mcp_projects()
|
|
221
|
+
```
|
|
222
|
+
|
|
223
|
+
**Webhook event server (HMAC-SHA256):**
|
|
224
|
+
|
|
225
|
+
```bash
|
|
226
|
+
export PYSTREAMMCP_WEBHOOK_SECRET="a long random shared secret"
|
|
227
|
+
```
|
|
228
|
+
|
|
229
|
+
Senders compute `HMAC-SHA256(secret, raw_request_body)` and send it as
|
|
230
|
+
`X-PyStreamMCP-Signature: sha256=<hex digest>`. Requests with a missing or invalid
|
|
231
|
+
signature are rejected with `401`; with no secret configured, the endpoint rejects every
|
|
232
|
+
request with `503`.
|
|
233
|
+
|
|
234
|
+
**Testing:**
|
|
235
|
+
|
|
236
|
+
```bash
|
|
237
|
+
pip install -e ".[dev,api,mcp,langchain,llamaindex,semantic-kernel]"
|
|
238
|
+
pytest tests/ -v
|
|
239
|
+
```
|
|
240
|
+
|
|
241
|
+
## Documentation
|
|
242
|
+
|
|
243
|
+
- [`ROADMAP_HONEST.md`](ROADMAP_HONEST.md) — full, unhedged status: what's tested, what's fabricated/broken, technical debt, what's explicitly not built
|
|
244
|
+
- [`docs/ARCHITECTURE.md`](docs/ARCHITECTURE.md) — how the shipped package is structured, with a diagram
|
|
245
|
+
- [`OKF_INTEGRATION.md`](OKF_INTEGRATION.md) — the OKF catalog/discovery/query-planner feature
|
|
246
|
+
- [`CHANGELOG.md`](CHANGELOG.md) — release history
|
|
247
|
+
- [`examples/`](examples/) — runnable examples, including framework integrations and the MCP orchestrator
|
|
248
|
+
|
|
249
|
+
## Contributing
|
|
250
|
+
|
|
251
|
+
Contributions are welcome. See [CONTRIBUTING.md](CONTRIBUTING.md) and
|
|
252
|
+
[CODE_OF_CONDUCT.md](CODE_OF_CONDUCT.md). Report security issues per
|
|
253
|
+
[SECURITY.md](SECURITY.md).
|
|
254
|
+
|
|
255
|
+
## Related projects
|
|
256
|
+
|
|
257
|
+
- [PyStreamXL](https://github.com/Mullassery/PyStreamXL) — stream large Excel workbooks with constant memory
|
|
258
|
+
- [PyStreamPDF](https://github.com/Mullassery/PyStreamPDF) — token-efficient PDF extraction for RAG
|
|
259
|
+
- [PyStreamMCP](https://github.com/Mullassery/PyStreamMCP) — context and token optimization for AI agents
|
|
260
|
+
- [PyStreamAI](https://github.com/Mullassery/PyStreamAI) — ML deployment toolkit (canary/A-B, cost tracking, ONNX)
|
|
261
|
+
- [PyTokenCalc](https://github.com/Mullassery/PyTokenCalc) — LLM token counting and cost estimation
|
|
262
|
+
- [Browse all projects](https://github.com/Mullassery?tab=repositories)
|
|
263
|
+
|
|
264
|
+
## License
|
|
265
|
+
|
|
266
|
+
This project is licensed under the [Apache License 2.0](LICENSE).
|
|
@@ -0,0 +1,203 @@
|
|
|
1
|
+
# PyStreamMCP
|
|
2
|
+
|
|
3
|
+
[](https://pypi.org/project/pystreammcp/)
|
|
4
|
+
[](https://github.com/Mullassery/PyStreamMCP/actions/workflows/ci.yml)
|
|
5
|
+
[](https://www.python.org)
|
|
6
|
+
[](./LICENSE)
|
|
7
|
+
|
|
8
|
+
Context and token optimization for AI agents — query planning, source discovery, and MCP orchestration.
|
|
9
|
+
|
|
10
|
+
## What it is
|
|
11
|
+
|
|
12
|
+
PyStreamMCP is an AI-agent intelligence layer: query planning, context discovery, and
|
|
13
|
+
token-cost optimization, exposed both as a Python SDK and as an MCP (Model Context
|
|
14
|
+
Protocol) tool server. It also includes a small event-driven orchestration/federation
|
|
15
|
+
layer for coordinating multiple MCP endpoints. The published package is **pure Python** —
|
|
16
|
+
`pip install` works with no Rust toolchain or compiler.
|
|
17
|
+
|
|
18
|
+
## Features / Highlights
|
|
19
|
+
|
|
20
|
+
- **Agent query planning** — `pystreammcp.Agent` with selectable optimization strategies
|
|
21
|
+
(`token_efficient`, `balanced`, `quality_first`) and token accounting.
|
|
22
|
+
- **Source discovery** — `SourceRegistry` ranks registered data sources by real
|
|
23
|
+
word-overlap relevance (Jaccard) to a query; backs REST `/discover`, the
|
|
24
|
+
`pystreammcp_discover` MCP tool, and `LangchainAdapter.discover()`.
|
|
25
|
+
- **MCP tool server** — `PyStreamMCPHandler` wires the MCP tool-call surface directly to a
|
|
26
|
+
live `Orchestrator`/`EventRouter`; MCP tool args are validated with Pydantic and the
|
|
27
|
+
advertised schema is generated from the same models.
|
|
28
|
+
- **MCP orchestration & federation** — `Orchestrator` probes each configured endpoint's
|
|
29
|
+
real `tools/list` MCP method, with lexical tool-relevance ranking and capability
|
|
30
|
+
matching.
|
|
31
|
+
- **Webhook event server** — `pystreammcp.server.create_flask_app()` exposes an
|
|
32
|
+
HMAC-SHA256-signed event endpoint; unsigned or invalid events are rejected, and the
|
|
33
|
+
endpoint fails closed (`503`) if no secret is configured.
|
|
34
|
+
- **Framework adapters** — LangChain, LlamaIndex, CrewAI, Semantic Kernel, PydanticAI,
|
|
35
|
+
and Haystack under `pystreammcp.integrations`.
|
|
36
|
+
- **CLI** — `pystreammcp` with `query` / `server` / `version` / `dashboard`.
|
|
37
|
+
- **OKF integration** — an Open Knowledge Format catalog/discovery/query-planner feature
|
|
38
|
+
(see [`OKF_INTEGRATION.md`](OKF_INTEGRATION.md)).
|
|
39
|
+
|
|
40
|
+
## Who it's for / Use cases
|
|
41
|
+
|
|
42
|
+
- **Giving an AI agent a query-planning layer over multiple data sources**, exposed as
|
|
43
|
+
real MCP tools rather than hand-rolled per-agent glue code.
|
|
44
|
+
- **Coordinating multiple MCP endpoints** through the event-driven
|
|
45
|
+
orchestration/federation layer instead of wiring each one separately.
|
|
46
|
+
- **Tracking token-cost optimization** across agent queries.
|
|
47
|
+
- **Adding MCP support to an existing agent framework** through the shipped adapters.
|
|
48
|
+
|
|
49
|
+
## What it is not
|
|
50
|
+
|
|
51
|
+
- **The Rust backend is not shipped.** `core/` and `python/src/lib.rs` are an in-progress
|
|
52
|
+
Rust workspace intended as a future performance backend; the wheel built from
|
|
53
|
+
`pyproject.toml` is pure Python. The workspace compiles and its tests pass, but it is
|
|
54
|
+
tracked separately and not part of the published package.
|
|
55
|
+
- **Some orchestration capabilities are not fully implemented.** Cross-project federated
|
|
56
|
+
query *execution* and cross-database joins currently report
|
|
57
|
+
`"status": "not_implemented"` with an explanation, rather than fabricated result rows.
|
|
58
|
+
- **Source discovery is a word-overlap heuristic, not semantic search.**
|
|
59
|
+
`SourceRegistry` uses Jaccard token overlap; wrap it with your own similarity scoring if
|
|
60
|
+
you need embeddings.
|
|
61
|
+
- **Optional concurrency/framework packages have Python constraints.** The core SDK
|
|
62
|
+
(`Agent`, `SourceRegistry`, `Orchestrator`) supports Python 3.9+, but the `mcp` and
|
|
63
|
+
`semantic-kernel` extras require Python 3.10+ (their upstream packages don't publish
|
|
64
|
+
3.9-compatible releases). CI tests 3.10, 3.11, and 3.12 only.
|
|
65
|
+
- **Known dependency CVEs.** `pip-audit` (run 2026-09-20) found 7 known CVEs in
|
|
66
|
+
transitive dependencies (`werkzeug` via `flask`, `nltk` via `llama-index`). See
|
|
67
|
+
[`ROADMAP_HONEST.md`](ROADMAP_HONEST.md) §4.
|
|
68
|
+
- **The HTTP servers have no auth layer of their own.** They bind to `127.0.0.1`
|
|
69
|
+
(localhost-only) by default; pass `host="0.0.0.0"` explicitly only inside a network
|
|
70
|
+
boundary you control. The event endpoint requires HMAC-SHA256 signatures. See
|
|
71
|
+
[SECURITY.md](SECURITY.md).
|
|
72
|
+
|
|
73
|
+
## Project status
|
|
74
|
+
|
|
75
|
+
**Beta.** Current version **3.3.1** (`Development Status :: 4 - Beta`). The pure-Python
|
|
76
|
+
package is the shipped artifact and is under active hardening; the Rust workspace compiles
|
|
77
|
+
and passes its tests but is not shipped. The most recent pass fixed the Rust build,
|
|
78
|
+
Python `ruff` findings, and a stale integration test — see
|
|
79
|
+
[`ROADMAP_HONEST.md`](ROADMAP_HONEST.md) for the unhedged status.
|
|
80
|
+
|
|
81
|
+
## Installation
|
|
82
|
+
|
|
83
|
+
```bash
|
|
84
|
+
pip install PyStreamMCP
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
Optional extras — install only what you need:
|
|
88
|
+
|
|
89
|
+
```bash
|
|
90
|
+
pip install "PyStreamMCP[api]" # FastAPI + Flask HTTP servers
|
|
91
|
+
pip install "PyStreamMCP[mcp]" # MCP protocol client library
|
|
92
|
+
pip install "PyStreamMCP[langchain]" # LangChain adapter
|
|
93
|
+
pip install "PyStreamMCP[llamaindex]" # LlamaIndex adapter
|
|
94
|
+
pip install "PyStreamMCP[semantic-kernel]" # Semantic Kernel adapter
|
|
95
|
+
pip install "PyStreamMCP[all-integrations]" # every framework adapter
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
Requires Python 3.9+ for the core SDK; the `mcp` and `semantic-kernel` extras require
|
|
99
|
+
Python 3.10+.
|
|
100
|
+
|
|
101
|
+
## Quick start
|
|
102
|
+
|
|
103
|
+
```python
|
|
104
|
+
from pystreammcp import Agent
|
|
105
|
+
|
|
106
|
+
agent = Agent(
|
|
107
|
+
agent_id="recommendation_engine",
|
|
108
|
+
name="Product Recommendation Engine",
|
|
109
|
+
optimization_strategy="token_efficient", # or "balanced" / "quality_first"
|
|
110
|
+
max_tokens=1000,
|
|
111
|
+
)
|
|
112
|
+
|
|
113
|
+
result = agent.query("What are the top 10 customers by lifetime value?")
|
|
114
|
+
|
|
115
|
+
print(f"Baseline tokens: {result.baseline_tokens}")
|
|
116
|
+
print(f"Optimized tokens: {result.optimized_tokens}")
|
|
117
|
+
print(f"Reduction: {result.cost_reduction_percent:.1f}%")
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
Token counts are estimated from the actual query text (a ~4-characters-per-token
|
|
121
|
+
heuristic) and the reduction is computed from the selected strategy — not a fixed number.
|
|
122
|
+
See [`examples/basic_usage.py`](examples/basic_usage.py) for a full walkthrough.
|
|
123
|
+
|
|
124
|
+
## Usage
|
|
125
|
+
|
|
126
|
+
**Data source discovery:**
|
|
127
|
+
|
|
128
|
+
```python
|
|
129
|
+
from pystreammcp import SourceRegistry
|
|
130
|
+
|
|
131
|
+
registry = SourceRegistry()
|
|
132
|
+
registry.register(
|
|
133
|
+
"orders_db",
|
|
134
|
+
description="customer order history and revenue by quarter",
|
|
135
|
+
type="database",
|
|
136
|
+
tags=["orders", "revenue"],
|
|
137
|
+
)
|
|
138
|
+
|
|
139
|
+
results = registry.discover("customer revenue by quarter")
|
|
140
|
+
# [{"name": "orders_db", "type": "database", "relevance": 0.4444, "matched_terms": [...]}]
|
|
141
|
+
```
|
|
142
|
+
|
|
143
|
+
**MCP orchestration & federation** (`pystreammcp.toml`):
|
|
144
|
+
|
|
145
|
+
```toml
|
|
146
|
+
[federation]
|
|
147
|
+
endpoints = [
|
|
148
|
+
"http://localhost:8765/mcp",
|
|
149
|
+
"http://localhost:8766/mcp",
|
|
150
|
+
]
|
|
151
|
+
```
|
|
152
|
+
|
|
153
|
+
```python
|
|
154
|
+
from pystreammcp import Orchestrator
|
|
155
|
+
|
|
156
|
+
orch = Orchestrator() # reads ./pystreammcp.toml
|
|
157
|
+
result = orch.discover_mcp_projects()
|
|
158
|
+
```
|
|
159
|
+
|
|
160
|
+
**Webhook event server (HMAC-SHA256):**
|
|
161
|
+
|
|
162
|
+
```bash
|
|
163
|
+
export PYSTREAMMCP_WEBHOOK_SECRET="a long random shared secret"
|
|
164
|
+
```
|
|
165
|
+
|
|
166
|
+
Senders compute `HMAC-SHA256(secret, raw_request_body)` and send it as
|
|
167
|
+
`X-PyStreamMCP-Signature: sha256=<hex digest>`. Requests with a missing or invalid
|
|
168
|
+
signature are rejected with `401`; with no secret configured, the endpoint rejects every
|
|
169
|
+
request with `503`.
|
|
170
|
+
|
|
171
|
+
**Testing:**
|
|
172
|
+
|
|
173
|
+
```bash
|
|
174
|
+
pip install -e ".[dev,api,mcp,langchain,llamaindex,semantic-kernel]"
|
|
175
|
+
pytest tests/ -v
|
|
176
|
+
```
|
|
177
|
+
|
|
178
|
+
## Documentation
|
|
179
|
+
|
|
180
|
+
- [`ROADMAP_HONEST.md`](ROADMAP_HONEST.md) — full, unhedged status: what's tested, what's fabricated/broken, technical debt, what's explicitly not built
|
|
181
|
+
- [`docs/ARCHITECTURE.md`](docs/ARCHITECTURE.md) — how the shipped package is structured, with a diagram
|
|
182
|
+
- [`OKF_INTEGRATION.md`](OKF_INTEGRATION.md) — the OKF catalog/discovery/query-planner feature
|
|
183
|
+
- [`CHANGELOG.md`](CHANGELOG.md) — release history
|
|
184
|
+
- [`examples/`](examples/) — runnable examples, including framework integrations and the MCP orchestrator
|
|
185
|
+
|
|
186
|
+
## Contributing
|
|
187
|
+
|
|
188
|
+
Contributions are welcome. See [CONTRIBUTING.md](CONTRIBUTING.md) and
|
|
189
|
+
[CODE_OF_CONDUCT.md](CODE_OF_CONDUCT.md). Report security issues per
|
|
190
|
+
[SECURITY.md](SECURITY.md).
|
|
191
|
+
|
|
192
|
+
## Related projects
|
|
193
|
+
|
|
194
|
+
- [PyStreamXL](https://github.com/Mullassery/PyStreamXL) — stream large Excel workbooks with constant memory
|
|
195
|
+
- [PyStreamPDF](https://github.com/Mullassery/PyStreamPDF) — token-efficient PDF extraction for RAG
|
|
196
|
+
- [PyStreamMCP](https://github.com/Mullassery/PyStreamMCP) — context and token optimization for AI agents
|
|
197
|
+
- [PyStreamAI](https://github.com/Mullassery/PyStreamAI) — ML deployment toolkit (canary/A-B, cost tracking, ONNX)
|
|
198
|
+
- [PyTokenCalc](https://github.com/Mullassery/PyTokenCalc) — LLM token counting and cost estimation
|
|
199
|
+
- [Browse all projects](https://github.com/Mullassery?tab=repositories)
|
|
200
|
+
|
|
201
|
+
## License
|
|
202
|
+
|
|
203
|
+
This project is licensed under the [Apache License 2.0](LICENSE).
|
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "PyStreamMCP"
|
|
7
|
-
version = "3.3.
|
|
7
|
+
version = "3.3.2"
|
|
8
8
|
description = "Intelligent MCP orchestration hub - Intent understanding, capability matching, tool ranking with cohesive foundation"
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
license = "Apache-2.0"
|