mcp-proxy-adapter 2.1.2__py3-none-any.whl → 2.1.4__py3-none-any.whl
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.
- {examples → mcp_proxy_adapter/examples}/openapi_server.py +35 -7
- {mcp_proxy_adapter-2.1.2.dist-info → mcp_proxy_adapter-2.1.4.dist-info}/METADATA +98 -2
- mcp_proxy_adapter-2.1.4.dist-info/RECORD +28 -0
- mcp_proxy_adapter-2.1.4.dist-info/top_level.txt +1 -0
- docs/README.md +0 -172
- docs/README_ru.md +0 -172
- docs/architecture.md +0 -251
- docs/architecture_ru.md +0 -343
- docs/command_development.md +0 -250
- docs/command_development_ru.md +0 -593
- docs/deployment.md +0 -251
- docs/deployment_ru.md +0 -1298
- docs/examples.md +0 -254
- docs/examples_ru.md +0 -401
- docs/mcp_proxy_adapter.md +0 -251
- docs/mcp_proxy_adapter_ru.md +0 -405
- docs/quickstart.md +0 -251
- docs/quickstart_ru.md +0 -397
- docs/testing.md +0 -255
- docs/testing_ru.md +0 -469
- docs/validation_ru.md +0 -287
- examples/mcp_proxy_config.json +0 -175
- mcp_proxy_adapter-2.1.2.dist-info/RECORD +0 -61
- mcp_proxy_adapter-2.1.2.dist-info/top_level.txt +0 -5
- scripts/code_analyzer/code_analyzer.py +0 -328
- scripts/code_analyzer/register_commands.py +0 -446
- scripts/publish.py +0 -85
- tests/conftest.py +0 -12
- tests/test_adapter.py +0 -529
- tests/test_adapter_coverage.py +0 -274
- tests/test_basic_dispatcher.py +0 -169
- tests/test_command_registry.py +0 -328
- tests/test_examples.py +0 -32
- tests/test_mcp_proxy_adapter.py +0 -568
- tests/test_mcp_proxy_adapter_basic.py +0 -262
- tests/test_part1.py +0 -348
- tests/test_part2.py +0 -524
- tests/test_schema.py +0 -358
- tests/test_simple_adapter.py +0 -251
- {examples → mcp_proxy_adapter/examples}/analyze_config.py +0 -0
- {examples → mcp_proxy_adapter/examples}/basic_integration.py +0 -0
- {examples → mcp_proxy_adapter/examples}/docstring_and_schema_example.py +0 -0
- {examples → mcp_proxy_adapter/examples}/extension_example.py +0 -0
- {examples → mcp_proxy_adapter/examples}/help_best_practices.py +0 -0
- {examples → mcp_proxy_adapter/examples}/help_usage.py +0 -0
- {examples → mcp_proxy_adapter/examples}/mcp_proxy_client.py +0 -0
- {examples → mcp_proxy_adapter/examples}/project_structure_example.py +0 -0
- {examples → mcp_proxy_adapter/examples}/testing_example.py +0 -0
- {mcp_proxy_adapter-2.1.2.dist-info → mcp_proxy_adapter-2.1.4.dist-info}/WHEEL +0 -0
- {mcp_proxy_adapter-2.1.2.dist-info → mcp_proxy_adapter-2.1.4.dist-info}/licenses/LICENSE +0 -0
docs/command_development.md
DELETED
@@ -1,250 +0,0 @@
|
|
1
|
-
# Command Development Guide
|
2
|
-
|
3
|
-
This guide describes best practices and recommendations for developing commands for the Command Registry system.
|
4
|
-
|
5
|
-
## Core Principles
|
6
|
-
|
7
|
-
When developing commands for Command Registry, follow these principles:
|
8
|
-
|
9
|
-
1. **Single Responsibility**: a command should do one thing and do it well
|
10
|
-
2. **Declarative**: a command should be self-documenting through type hints and docstrings
|
11
|
-
3. **Independence**: a command should not depend on other commands
|
12
|
-
4. **Idempotency**: repeated execution of a command with the same parameters should yield identical results
|
13
|
-
5. **Validation**: a command should validate input data before execution
|
14
|
-
|
15
|
-
## Command Structure
|
16
|
-
|
17
|
-
Recommended command structure:
|
18
|
-
|
19
|
-
```python
|
20
|
-
from typing import Dict, List, Optional, Any, Union, Tuple
|
21
|
-
import logging
|
22
|
-
|
23
|
-
logger = logging.getLogger(__name__)
|
24
|
-
|
25
|
-
def command_name(
|
26
|
-
required_param: str,
|
27
|
-
optional_param: Optional[int] = None,
|
28
|
-
*,
|
29
|
-
keyword_only_param: bool = False
|
30
|
-
) -> Dict[str, Any]:
|
31
|
-
"""
|
32
|
-
Brief command description (one sentence).
|
33
|
-
|
34
|
-
Detailed command description explaining its purpose,
|
35
|
-
operational features, and possible side effects.
|
36
|
-
|
37
|
-
Args:
|
38
|
-
required_param: Description of required parameter
|
39
|
-
optional_param: Description of optional parameter
|
40
|
-
keyword_only_param: Description of keyword-only parameter
|
41
|
-
|
42
|
-
Returns:
|
43
|
-
Description of return value
|
44
|
-
|
45
|
-
Raises:
|
46
|
-
ValueError: When validation error occurs
|
47
|
-
RuntimeError: When execution error occurs
|
48
|
-
|
49
|
-
Examples:
|
50
|
-
>>> command_name("value", 42, keyword_only_param=True)
|
51
|
-
{'status': 'success', 'result': 'value_processed'}
|
52
|
-
"""
|
53
|
-
# Log execution start
|
54
|
-
logger.debug(f"Executing command_name with params: {required_param}, {optional_param}, {keyword_only_param}")
|
55
|
-
|
56
|
-
# Parameter validation
|
57
|
-
if not required_param:
|
58
|
-
raise ValueError("required_param cannot be empty")
|
59
|
-
|
60
|
-
if optional_param is not None and optional_param < 0:
|
61
|
-
raise ValueError("optional_param must be non-negative")
|
62
|
-
|
63
|
-
# Execute main logic
|
64
|
-
try:
|
65
|
-
# Main command logic
|
66
|
-
result = process_data(required_param, optional_param, keyword_only_param)
|
67
|
-
|
68
|
-
# Log successful execution
|
69
|
-
logger.info(f"Command command_name executed successfully with result: {result}")
|
70
|
-
|
71
|
-
return {
|
72
|
-
"status": "success",
|
73
|
-
"result": result
|
74
|
-
}
|
75
|
-
except Exception as e:
|
76
|
-
# Log error
|
77
|
-
logger.error(f"Error executing command command_name: {str(e)}", exc_info=True)
|
78
|
-
|
79
|
-
# Propagate exception for handling above
|
80
|
-
raise RuntimeError(f"Failed to execute command: {str(e)}") from e
|
81
|
-
```
|
82
|
-
|
83
|
-
## Best Practices
|
84
|
-
|
85
|
-
### Type Hints
|
86
|
-
|
87
|
-
1. **Use type hints for all parameters and return values**:
|
88
|
-
|
89
|
-
```python
|
90
|
-
def process_data(data: List[Dict[str, Any]], limit: Optional[int] = None) -> Tuple[List[Dict[str, Any]], int]:
|
91
|
-
# ...
|
92
|
-
```
|
93
|
-
|
94
|
-
2. **Use complex types from the `typing` module**:
|
95
|
-
|
96
|
-
```python
|
97
|
-
from typing import Dict, List, Optional, Union, Callable, TypeVar, Generic
|
98
|
-
|
99
|
-
T = TypeVar('T')
|
100
|
-
|
101
|
-
def filter_items(
|
102
|
-
items: List[T],
|
103
|
-
predicate: Callable[[T], bool]
|
104
|
-
) -> List[T]:
|
105
|
-
# ...
|
106
|
-
```
|
107
|
-
|
108
|
-
3. **Define your own types for complex structures**:
|
109
|
-
|
110
|
-
```python
|
111
|
-
from typing import Dict, List, TypedDict, Optional
|
112
|
-
|
113
|
-
class UserData(TypedDict):
|
114
|
-
id: str
|
115
|
-
name: str
|
116
|
-
email: str
|
117
|
-
roles: List[str]
|
118
|
-
profile: Optional[Dict[str, str]]
|
119
|
-
|
120
|
-
def get_user(user_id: str) -> UserData:
|
121
|
-
# ...
|
122
|
-
```
|
123
|
-
|
124
|
-
### Documentation
|
125
|
-
|
126
|
-
1. **Use docstrings to describe the command, its parameters, and return value**:
|
127
|
-
|
128
|
-
```python
|
129
|
-
def calculate_total(prices: List[float], discount: float = 0.0) -> float:
|
130
|
-
"""
|
131
|
-
Calculates total cost with discount.
|
132
|
-
|
133
|
-
Args:
|
134
|
-
prices: List of item prices
|
135
|
-
discount: Discount percentage (from 0.0 to 1.0)
|
136
|
-
|
137
|
-
Returns:
|
138
|
-
Total cost with discount
|
139
|
-
|
140
|
-
Raises:
|
141
|
-
ValueError: If discount is not in range [0, 1]
|
142
|
-
"""
|
143
|
-
```
|
144
|
-
|
145
|
-
2. **Add usage examples in docstring**:
|
146
|
-
|
147
|
-
```python
|
148
|
-
def calculate_total(prices: List[float], discount: float = 0.0) -> float:
|
149
|
-
"""
|
150
|
-
...
|
151
|
-
|
152
|
-
Examples:
|
153
|
-
>>> calculate_total([10.0, 20.0, 30.0])
|
154
|
-
60.0
|
155
|
-
>>> calculate_total([10.0, 20.0, 30.0], discount=0.1)
|
156
|
-
54.0
|
157
|
-
"""
|
158
|
-
```
|
159
|
-
|
160
|
-
### Parameter Validation
|
161
|
-
|
162
|
-
1. **Check parameter correctness at the beginning of the function**:
|
163
|
-
|
164
|
-
```python
|
165
|
-
def update_user(user_id: str, name: Optional[str] = None, email: Optional[str] = None) -> Dict[str, Any]:
|
166
|
-
"""Updates user information."""
|
167
|
-
if not user_id:
|
168
|
-
raise ValueError("user_id cannot be empty")
|
169
|
-
|
170
|
-
if email is not None and "@" not in email:
|
171
|
-
raise ValueError("Invalid email format")
|
172
|
-
|
173
|
-
# Main logic...
|
174
|
-
```
|
175
|
-
|
176
|
-
2. **Use libraries for complex data validation**:
|
177
|
-
|
178
|
-
```python
|
179
|
-
from pydantic import BaseModel, EmailStr, validator
|
180
|
-
|
181
|
-
class UserUpdateParams(BaseModel):
|
182
|
-
user_id: str
|
183
|
-
name: Optional[str] = None
|
184
|
-
email: Optional[EmailStr] = None
|
185
|
-
|
186
|
-
@validator('user_id')
|
187
|
-
def user_id_must_not_be_empty(cls, v):
|
188
|
-
if not v:
|
189
|
-
raise ValueError('user_id cannot be empty')
|
190
|
-
return v
|
191
|
-
|
192
|
-
def update_user(params: UserUpdateParams) -> Dict[str, Any]:
|
193
|
-
# Pydantic has already performed validation
|
194
|
-
# Main logic...
|
195
|
-
```
|
196
|
-
|
197
|
-
### Error Handling
|
198
|
-
|
199
|
-
1. **Use specific exception types**:
|
200
|
-
|
201
|
-
```python
|
202
|
-
def get_user(user_id: str) -> Dict[str, Any]:
|
203
|
-
if not user_id:
|
204
|
-
raise ValueError("user_id cannot be empty")
|
205
|
-
|
206
|
-
user = db.find_user(user_id)
|
207
|
-
if user is None:
|
208
|
-
raise UserNotFoundError(f"User with id {user_id} not found")
|
209
|
-
|
210
|
-
return user
|
211
|
-
```
|
212
|
-
|
213
|
-
2. **Preserve error context using exception chaining**:
|
214
|
-
|
215
|
-
```python
|
216
|
-
def process_order(order_id: str) -> Dict[str, Any]:
|
217
|
-
try:
|
218
|
-
order = get_order(order_id)
|
219
|
-
# Order processing...
|
220
|
-
except OrderNotFoundError as e:
|
221
|
-
raise ProcessingError(f"Failed to process order {order_id}") from e
|
222
|
-
except Exception as e:
|
223
|
-
raise ProcessingError(f"Unexpected error while processing order {order_id}") from e
|
224
|
-
```
|
225
|
-
|
226
|
-
### Logging
|
227
|
-
|
228
|
-
1. **Use logging to track command execution progress**:
|
229
|
-
|
230
|
-
```python
|
231
|
-
import logging
|
232
|
-
|
233
|
-
logger = logging.getLogger(__name__)
|
234
|
-
|
235
|
-
def complex_operation(data: Dict[str, Any]) -> Dict[str, Any]:
|
236
|
-
logger.info(f"Starting complex operation with data: {data}")
|
237
|
-
|
238
|
-
try:
|
239
|
-
# Step 1
|
240
|
-
logger.debug("Performing step 1")
|
241
|
-
result_1 = step_1(data)
|
242
|
-
|
243
|
-
# Step 2
|
244
|
-
logger.debug("Performing step 2")
|
245
|
-
result_2 = step_2(result_1)
|
246
|
-
|
247
|
-
# Final step
|
248
|
-
logger.debug("Performing final step")
|
249
|
-
final_result = final_step(result_2)
|
250
|
-
```
|