mcp-proxy-adapter 6.4.44__tar.gz → 6.4.45__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.
Files changed (142) hide show
  1. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/PKG-INFO +81 -1
  2. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/README.md +80 -0
  3. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/proxy_registration.py +100 -68
  4. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/bugfix_certificate_config.py +284 -0
  5. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/cert_manager_bugfix.py +203 -0
  6. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/config_builder.py +574 -0
  7. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/config_cli.py +283 -0
  8. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/create_test_configs.py +220 -0
  9. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/generate_certificates_bugfix.py +374 -0
  10. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/generate_certificates_cli.py +406 -0
  11. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/generate_certificates_fixed.py +313 -0
  12. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/generate_certificates_framework.py +366 -0
  13. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/generate_certificates_openssl.py +391 -0
  14. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/required_certificates.py +210 -0
  15. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/run_full_test_suite.py +117 -13
  16. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/run_security_tests_fixed.py +42 -26
  17. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/security_test_client.py +332 -85
  18. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/test_config_builder.py +450 -0
  19. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter/examples/update_config_certificates.py +136 -0
  20. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/version.py +1 -1
  21. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter.egg-info/PKG-INFO +81 -1
  22. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter.egg-info/SOURCES.txt +24 -0
  23. mcp_proxy_adapter-6.4.45/mcp_proxy_adapter.egg-info/entry_points.txt +12 -0
  24. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/pyproject.toml +11 -1
  25. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/setup.py +7 -0
  26. mcp_proxy_adapter-6.4.44/mcp_proxy_adapter/examples/create_test_configs.py +0 -317
  27. mcp_proxy_adapter-6.4.44/mcp_proxy_adapter.egg-info/entry_points.txt +0 -2
  28. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/__init__.py +0 -0
  29. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/__main__.py +0 -0
  30. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/__init__.py +0 -0
  31. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/app.py +0 -0
  32. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/handlers.py +0 -0
  33. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/__init__.py +0 -0
  34. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/base.py +0 -0
  35. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/command_permission_middleware.py +0 -0
  36. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/error_handling.py +0 -0
  37. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/factory.py +0 -0
  38. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/logging.py +0 -0
  39. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/performance.py +0 -0
  40. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/protocol_middleware.py +0 -0
  41. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/transport_middleware.py +0 -0
  42. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/unified_security.py +0 -0
  43. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/middleware/user_info_middleware.py +0 -0
  44. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/schemas.py +0 -0
  45. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/tool_integration.py +0 -0
  46. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/api/tools.py +0 -0
  47. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/__init__.py +0 -0
  48. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/auth_validation_command.py +0 -0
  49. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/base.py +0 -0
  50. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/builtin_commands.py +0 -0
  51. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/catalog_manager.py +0 -0
  52. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/cert_monitor_command.py +0 -0
  53. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/certificate_management_command.py +0 -0
  54. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/command_registry.py +0 -0
  55. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/config_command.py +0 -0
  56. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/dependency_container.py +0 -0
  57. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/dependency_manager.py +0 -0
  58. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/echo_command.py +0 -0
  59. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/health_command.py +0 -0
  60. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/help_command.py +0 -0
  61. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/hooks.py +0 -0
  62. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/key_management_command.py +0 -0
  63. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/load_command.py +0 -0
  64. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/plugins_command.py +0 -0
  65. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/protocol_management_command.py +0 -0
  66. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/proxy_registration_command.py +0 -0
  67. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/reload_command.py +0 -0
  68. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/result.py +0 -0
  69. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/role_test_command.py +0 -0
  70. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/roles_management_command.py +0 -0
  71. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/security_command.py +0 -0
  72. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/settings_command.py +0 -0
  73. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/ssl_setup_command.py +0 -0
  74. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/token_management_command.py +0 -0
  75. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/transport_management_command.py +0 -0
  76. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/commands/unload_command.py +0 -0
  77. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/config.py +0 -0
  78. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/__init__.py +0 -0
  79. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/app_factory.py +0 -0
  80. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/app_runner.py +0 -0
  81. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/auth_validator.py +0 -0
  82. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/certificate_utils.py +0 -0
  83. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/client.py +0 -0
  84. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/client_manager.py +0 -0
  85. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/client_security.py +0 -0
  86. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/config_converter.py +0 -0
  87. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/config_validator.py +0 -0
  88. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/crl_utils.py +0 -0
  89. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/errors.py +0 -0
  90. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/logging.py +0 -0
  91. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/mtls_asgi.py +0 -0
  92. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/mtls_asgi_app.py +0 -0
  93. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/mtls_server.py +0 -0
  94. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/protocol_manager.py +0 -0
  95. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/proxy_client.py +0 -0
  96. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/role_utils.py +0 -0
  97. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/security_adapter.py +0 -0
  98. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/security_factory.py +0 -0
  99. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/security_integration.py +0 -0
  100. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/server_adapter.py +0 -0
  101. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/server_engine.py +0 -0
  102. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/settings.py +0 -0
  103. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/ssl_utils.py +0 -0
  104. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/transport_manager.py +0 -0
  105. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/unified_config_adapter.py +0 -0
  106. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/core/utils.py +0 -0
  107. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/custom_openapi.py +0 -0
  108. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/__init__.py +0 -0
  109. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/basic_framework/__init__.py +0 -0
  110. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/basic_framework/commands/__init__.py +0 -0
  111. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/basic_framework/hooks/__init__.py +0 -0
  112. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/basic_framework/main.py +0 -0
  113. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/commands/__init__.py +0 -0
  114. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/debug_request_state.py +0 -0
  115. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/debug_role_chain.py +0 -0
  116. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/demo_client.py +0 -0
  117. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/full_application/__init__.py +0 -0
  118. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/full_application/commands/__init__.py +0 -0
  119. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/full_application/commands/custom_echo_command.py +0 -0
  120. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/full_application/commands/dynamic_calculator_command.py +0 -0
  121. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/full_application/hooks/__init__.py +0 -0
  122. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/full_application/hooks/application_hooks.py +0 -0
  123. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/full_application/hooks/builtin_command_hooks.py +0 -0
  124. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/full_application/main.py +0 -0
  125. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/full_application/proxy_endpoints.py +0 -0
  126. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/generate_all_certificates.py +0 -0
  127. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/proxy_registration_example.py +0 -0
  128. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/run_example.py +0 -0
  129. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/run_proxy_server.py +0 -0
  130. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/setup_test_environment.py +0 -0
  131. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/simple_protocol_test.py +0 -0
  132. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/test_config.py +0 -0
  133. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/test_examples.py +0 -0
  134. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/test_protocol_examples.py +0 -0
  135. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/examples/universal_client.py +0 -0
  136. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/main.py +0 -0
  137. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter/openapi.py +0 -0
  138. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter.egg-info/dependency_links.txt +0 -0
  139. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter.egg-info/not-zip-safe +0 -0
  140. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter.egg-info/requires.txt +0 -0
  141. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/mcp_proxy_adapter.egg-info/top_level.txt +0 -0
  142. {mcp_proxy_adapter-6.4.44 → mcp_proxy_adapter-6.4.45}/setup.cfg +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: mcp-proxy-adapter
3
- Version: 6.4.44
3
+ Version: 6.4.45
4
4
  Summary: Powerful JSON-RPC microservices framework with built-in security, authentication, and proxy registration
5
5
  Home-page: https://github.com/maverikod/mcp-proxy-adapter
6
6
  Author: Vasiliy Zdanovskiy
@@ -138,6 +138,86 @@ The `mcp_proxy_adapter/examples/` directory contains comprehensive examples for
138
138
  - **Security Testing**: Comprehensive security test suite
139
139
  - **Certificate Generation**: SSL/TLS certificate management
140
140
 
141
+ ### Test Environment Setup
142
+
143
+ The framework includes a comprehensive test environment setup that automatically creates configurations, generates certificates, and runs tests:
144
+
145
+ ```bash
146
+ # Create a complete test environment with all configurations and certificates
147
+ python -m mcp_proxy_adapter.examples.setup_test_environment
148
+
149
+ # Create test environment in a specific directory
150
+ python -m mcp_proxy_adapter.examples.setup_test_environment /path/to/test/dir
151
+
152
+ # Skip certificate generation (use existing certificates)
153
+ python -m mcp_proxy_adapter.examples.setup_test_environment --skip-certs
154
+
155
+ # Skip running tests (setup only)
156
+ python -m mcp_proxy_adapter.examples.setup_test_environment --skip-tests
157
+ ```
158
+
159
+ ### Configuration Generation
160
+
161
+ Generate test configurations from a comprehensive template:
162
+
163
+ ```bash
164
+ # Generate all test configurations
165
+ python -m mcp_proxy_adapter.examples.create_test_configs
166
+
167
+ # Generate from specific comprehensive config
168
+ python -m mcp_proxy_adapter.examples.create_test_configs --comprehensive-config config.json
169
+
170
+ # Generate specific configuration types
171
+ python -m mcp_proxy_adapter.examples.create_test_configs --types http,https,mtls
172
+ ```
173
+
174
+ ### Certificate Generation
175
+
176
+ Generate SSL/TLS certificates for testing:
177
+
178
+ ```bash
179
+ # Generate all certificates using mcp_security_framework
180
+ python -m mcp_proxy_adapter.examples.generate_all_certificates
181
+
182
+ # Generate certificates with custom configuration
183
+ python -m mcp_proxy_adapter.examples.generate_certificates_framework --config cert_config.json
184
+ ```
185
+
186
+ ### Security Testing
187
+
188
+ Run comprehensive security tests:
189
+
190
+ ```bash
191
+ # Run all security tests
192
+ python -m mcp_proxy_adapter.examples.run_security_tests_fixed
193
+
194
+ # Run full test suite (includes setup, config generation, certificate generation, and testing)
195
+ python -m mcp_proxy_adapter.examples.run_full_test_suite
196
+ ```
197
+
198
+ ### Complete Workflow Example
199
+
200
+ ```bash
201
+ # 1. Install the package
202
+ pip install mcp-proxy-adapter
203
+
204
+ # 2. Create test environment (automatically runs tests)
205
+ python -m mcp_proxy_adapter.examples.setup_test_environment
206
+
207
+ # 3. Or run individual steps:
208
+ # Generate certificates
209
+ python -m mcp_proxy_adapter.examples.generate_all_certificates
210
+
211
+ # Generate configurations
212
+ python -m mcp_proxy_adapter.examples.create_test_configs
213
+
214
+ # Run security tests
215
+ python -m mcp_proxy_adapter.examples.run_security_tests_fixed
216
+
217
+ # 4. Start server with generated configuration
218
+ python -m mcp_proxy_adapter --config configs/http_simple.json
219
+ ```
220
+
141
221
  ## Development
142
222
 
143
223
  The project follows a modular architecture:
@@ -79,6 +79,86 @@ The `mcp_proxy_adapter/examples/` directory contains comprehensive examples for
79
79
  - **Security Testing**: Comprehensive security test suite
80
80
  - **Certificate Generation**: SSL/TLS certificate management
81
81
 
82
+ ### Test Environment Setup
83
+
84
+ The framework includes a comprehensive test environment setup that automatically creates configurations, generates certificates, and runs tests:
85
+
86
+ ```bash
87
+ # Create a complete test environment with all configurations and certificates
88
+ python -m mcp_proxy_adapter.examples.setup_test_environment
89
+
90
+ # Create test environment in a specific directory
91
+ python -m mcp_proxy_adapter.examples.setup_test_environment /path/to/test/dir
92
+
93
+ # Skip certificate generation (use existing certificates)
94
+ python -m mcp_proxy_adapter.examples.setup_test_environment --skip-certs
95
+
96
+ # Skip running tests (setup only)
97
+ python -m mcp_proxy_adapter.examples.setup_test_environment --skip-tests
98
+ ```
99
+
100
+ ### Configuration Generation
101
+
102
+ Generate test configurations from a comprehensive template:
103
+
104
+ ```bash
105
+ # Generate all test configurations
106
+ python -m mcp_proxy_adapter.examples.create_test_configs
107
+
108
+ # Generate from specific comprehensive config
109
+ python -m mcp_proxy_adapter.examples.create_test_configs --comprehensive-config config.json
110
+
111
+ # Generate specific configuration types
112
+ python -m mcp_proxy_adapter.examples.create_test_configs --types http,https,mtls
113
+ ```
114
+
115
+ ### Certificate Generation
116
+
117
+ Generate SSL/TLS certificates for testing:
118
+
119
+ ```bash
120
+ # Generate all certificates using mcp_security_framework
121
+ python -m mcp_proxy_adapter.examples.generate_all_certificates
122
+
123
+ # Generate certificates with custom configuration
124
+ python -m mcp_proxy_adapter.examples.generate_certificates_framework --config cert_config.json
125
+ ```
126
+
127
+ ### Security Testing
128
+
129
+ Run comprehensive security tests:
130
+
131
+ ```bash
132
+ # Run all security tests
133
+ python -m mcp_proxy_adapter.examples.run_security_tests_fixed
134
+
135
+ # Run full test suite (includes setup, config generation, certificate generation, and testing)
136
+ python -m mcp_proxy_adapter.examples.run_full_test_suite
137
+ ```
138
+
139
+ ### Complete Workflow Example
140
+
141
+ ```bash
142
+ # 1. Install the package
143
+ pip install mcp-proxy-adapter
144
+
145
+ # 2. Create test environment (automatically runs tests)
146
+ python -m mcp_proxy_adapter.examples.setup_test_environment
147
+
148
+ # 3. Or run individual steps:
149
+ # Generate certificates
150
+ python -m mcp_proxy_adapter.examples.generate_all_certificates
151
+
152
+ # Generate configurations
153
+ python -m mcp_proxy_adapter.examples.create_test_configs
154
+
155
+ # Run security tests
156
+ python -m mcp_proxy_adapter.examples.run_security_tests_fixed
157
+
158
+ # 4. Start server with generated configuration
159
+ python -m mcp_proxy_adapter --config configs/http_simple.json
160
+ ```
161
+
82
162
  ## Development
83
163
 
84
164
  The project follows a modular architecture:
@@ -68,84 +68,116 @@ class ProxyRegistrationManager:
68
68
  except Exception:
69
69
  pass
70
70
 
71
- # Basic registration settings
72
- self.proxy_url = self.registration_config.get("proxy_url")
73
- if not self.proxy_url:
74
- raise ValueError(
75
- "proxy_url is required in registration configuration. "
76
- "Please specify a valid proxy URL in your configuration."
77
- )
78
- self.server_id = self.registration_config.get("server_id")
79
- if not self.server_id:
80
- # Try to get from proxy_info.name as fallback
81
- self.server_id = self.registration_config.get("proxy_info", {}).get("name")
82
- if not self.server_id:
71
+ # Check if registration is enabled
72
+ self.enabled = self.registration_config.get("enabled", False)
73
+
74
+ # Basic registration settings - only validate if enabled
75
+ if self.enabled:
76
+ self.proxy_url = self.registration_config.get("proxy_url")
77
+ if not self.proxy_url:
83
78
  raise ValueError(
84
- "server_id is required in registration configuration. "
85
- "Please specify a server_id or proxy_info.name in your configuration."
79
+ "proxy_url is required in registration configuration. "
80
+ "Please specify a valid proxy URL in your configuration."
86
81
  )
87
- self.server_name = self.registration_config.get("server_name")
88
- if not self.server_name:
89
- # Try to get from proxy_info.name as fallback
90
- self.server_name = self.registration_config.get("proxy_info", {}).get("name")
82
+ else:
83
+ self.proxy_url = None
84
+
85
+ if self.enabled:
86
+ self.server_id = self.registration_config.get("server_id")
87
+ if not self.server_id:
88
+ # Try to get from proxy_info.name as fallback
89
+ self.server_id = self.registration_config.get("proxy_info", {}).get("name")
90
+ if not self.server_id:
91
+ raise ValueError(
92
+ "server_id is required in registration configuration. "
93
+ "Please specify a server_id or proxy_info.name in your configuration."
94
+ )
95
+ self.server_name = self.registration_config.get("server_name")
91
96
  if not self.server_name:
97
+ # Try to get from proxy_info.name as fallback
98
+ self.server_name = self.registration_config.get("proxy_info", {}).get("name")
99
+ if not self.server_name:
100
+ raise ValueError(
101
+ "server_name is required in registration configuration. "
102
+ "Please specify a server_name or proxy_info.name in your configuration."
103
+ )
104
+ self.description = self.registration_config.get("description")
105
+ if not self.description:
106
+ # Try to get from proxy_info.description as fallback
107
+ self.description = self.registration_config.get("proxy_info", {}).get("description")
108
+ if not self.description:
109
+ raise ValueError(
110
+ "description is required in registration configuration. "
111
+ "Please specify a description or proxy_info.description in your configuration."
112
+ )
113
+ else:
114
+ self.server_id = None
115
+ self.server_name = None
116
+ self.description = None
117
+
118
+ if self.enabled:
119
+ self.version = self.registration_config.get("version")
120
+ if not self.version:
121
+ # Try to get from proxy_info.version as fallback
122
+ self.version = self.registration_config.get("proxy_info", {}).get("version")
123
+ if not self.version:
124
+ raise ValueError(
125
+ "version is required in registration configuration. "
126
+ "Please specify a version or proxy_info.version in your configuration."
127
+ )
128
+ else:
129
+ self.version = None
130
+
131
+ # Heartbeat settings - only validate if enabled
132
+ if self.enabled:
133
+ heartbeat_config = self.registration_config.get("heartbeat", {})
134
+ self.timeout = heartbeat_config.get("timeout")
135
+ if self.timeout is None:
92
136
  raise ValueError(
93
- "server_name is required in registration configuration. "
94
- "Please specify a server_name or proxy_info.name in your configuration."
137
+ "heartbeat.timeout is required in registration configuration. "
138
+ "Please specify a timeout value."
95
139
  )
96
- self.description = self.registration_config.get("description")
97
- if not self.description:
98
- # Try to get from proxy_info.description as fallback
99
- self.description = self.registration_config.get("proxy_info", {}).get("description")
100
- if not self.description:
140
+ self.retry_attempts = heartbeat_config.get("retry_attempts")
141
+ if self.retry_attempts is None:
101
142
  raise ValueError(
102
- "description is required in registration configuration. "
103
- "Please specify a description or proxy_info.description in your configuration."
143
+ "heartbeat.retry_attempts is required in registration configuration. "
144
+ "Please specify a retry_attempts value."
104
145
  )
105
- self.version = self.registration_config.get("version")
106
- if not self.version:
107
- # Try to get from proxy_info.version as fallback
108
- self.version = self.registration_config.get("proxy_info", {}).get("version")
109
- if not self.version:
146
+ else:
147
+ self.timeout = None
148
+ self.retry_attempts = None
149
+
150
+ if self.enabled:
151
+ self.retry_delay = heartbeat_config.get("retry_delay")
152
+ if self.retry_delay is None:
110
153
  raise ValueError(
111
- "version is required in registration configuration. "
112
- "Please specify a version or proxy_info.version in your configuration."
154
+ "heartbeat.retry_delay is required in registration configuration. "
155
+ "Please specify a retry_delay value."
113
156
  )
114
-
115
- # Heartbeat settings
116
- heartbeat_config = self.registration_config.get("heartbeat", {})
117
- self.timeout = heartbeat_config.get("timeout")
118
- if self.timeout is None:
119
- raise ValueError(
120
- "heartbeat.timeout is required in registration configuration. "
121
- "Please specify a timeout value."
122
- )
123
- self.retry_attempts = heartbeat_config.get("retry_attempts")
124
- if self.retry_attempts is None:
125
- raise ValueError(
126
- "heartbeat.retry_attempts is required in registration configuration. "
127
- "Please specify a retry_attempts value."
128
- )
129
- self.retry_delay = heartbeat_config.get("retry_delay")
130
- if self.retry_delay is None:
131
- raise ValueError(
132
- "heartbeat.retry_delay is required in registration configuration. "
133
- "Please specify a retry_delay value."
134
- )
135
- self.heartbeat_interval = heartbeat_config.get("interval")
136
- if self.heartbeat_interval is None:
137
- raise ValueError(
138
- "heartbeat.interval is required in registration configuration. "
139
- "Please specify an interval value."
140
- )
157
+ else:
158
+ self.retry_delay = None
159
+
160
+ if self.enabled:
161
+ self.heartbeat_interval = heartbeat_config.get("interval")
162
+ if self.heartbeat_interval is None:
163
+ raise ValueError(
164
+ "heartbeat.interval is required in registration configuration. "
165
+ "Please specify an interval value."
166
+ )
167
+ else:
168
+ self.heartbeat_interval = None
141
169
 
142
170
  # Auto registration settings
143
- self.auto_register = self.registration_config.get("enabled")
144
- if self.auto_register is None:
145
- raise ValueError(
146
- "enabled is required in registration configuration. "
147
- "Please specify whether registration is enabled (true/false)."
148
- )
171
+ if self.enabled:
172
+ self.auto_register = self.registration_config.get("enabled")
173
+ if self.auto_register is None:
174
+ raise ValueError(
175
+ "enabled is required in registration configuration. "
176
+ "Please specify whether registration is enabled (true/false)."
177
+ )
178
+ else:
179
+ self.auto_register = False
180
+
149
181
  self.auto_unregister = True # Always unregister on shutdown
150
182
 
151
183
  # Initialize client security manager
@@ -168,7 +200,7 @@ class ProxyRegistrationManager:
168
200
  Returns:
169
201
  True if registration is enabled, False otherwise.
170
202
  """
171
- return self.registration_config.get("enabled", False)
203
+ return self.enabled
172
204
 
173
205
  def set_server_url(self, server_url: str) -> None:
174
206
  """
@@ -0,0 +1,284 @@
1
+ #!/usr/bin/env python3
2
+ """
3
+ Bugfix for mcp_security_framework CertificateConfig
4
+ This script provides a fix for the CertificateConfig validation issue.
5
+
6
+ ISSUE: CertificateConfig requires CA certificate and key paths even when creating a CA certificate.
7
+ This creates a chicken-and-egg problem where you need a CA to create a CA.
8
+
9
+ SOLUTION: Modify the validation logic to allow CA creation mode.
10
+
11
+ Author: Vasiliy Zdanovskiy
12
+ email: vasilyvz@gmail.com
13
+ """
14
+
15
+ import sys
16
+ from pathlib import Path
17
+ from typing import Optional
18
+ from pydantic import BaseModel, Field, field_validator, model_validator
19
+
20
+
21
+ class FixedCertificateConfig(BaseModel):
22
+ """
23
+ Fixed Certificate Management Configuration Model
24
+
25
+ This model defines certificate management configuration settings
26
+ including CA settings, certificate storage, and validation options.
27
+
28
+ BUGFIX: Added ca_creation_mode to allow CA certificate creation
29
+ without requiring existing CA paths.
30
+
31
+ Attributes:
32
+ enabled: Whether certificate management is enabled
33
+ ca_creation_mode: Whether we are in CA creation mode (bypasses CA path validation)
34
+ ca_cert_path: Path to CA certificate
35
+ ca_key_path: Path to CA private key
36
+ cert_storage_path: Path for certificate storage
37
+ key_storage_path: Path for private key storage
38
+ default_validity_days: Default certificate validity in days
39
+ key_size: RSA key size for generated certificates
40
+ hash_algorithm: Hash algorithm for certificate signing
41
+ crl_enabled: Whether CRL is enabled
42
+ crl_path: Path for CRL storage
43
+ crl_validity_days: CRL validity period in days
44
+ auto_renewal: Whether automatic certificate renewal is enabled
45
+ renewal_threshold_days: Days before expiry to renew
46
+ """
47
+
48
+ enabled: bool = Field(
49
+ default=False, description="Whether certificate management is enabled"
50
+ )
51
+ ca_creation_mode: bool = Field(
52
+ default=False, description="Whether we are in CA creation mode (bypasses CA path validation)"
53
+ )
54
+ ca_cert_path: Optional[str] = Field(
55
+ default=None, description="Path to CA certificate"
56
+ )
57
+ ca_key_path: Optional[str] = Field(
58
+ default=None, description="Path to CA private key"
59
+ )
60
+ cert_storage_path: str = Field(
61
+ default="./certs", description="Path for certificate storage"
62
+ )
63
+ key_storage_path: str = Field(
64
+ default="./keys", description="Path for private key storage"
65
+ )
66
+ default_validity_days: int = Field(
67
+ default=365, ge=1, le=3650, description="Default certificate validity in days"
68
+ )
69
+ key_size: int = Field(
70
+ default=2048,
71
+ ge=1024,
72
+ le=4096,
73
+ description="RSA key size for generated certificates",
74
+ )
75
+ hash_algorithm: str = Field(
76
+ default="sha256", description="Hash algorithm for certificate signing"
77
+ )
78
+ crl_enabled: bool = Field(default=False, description="Whether CRL is enabled")
79
+ crl_path: Optional[str] = Field(default=None, description="Path for CRL storage")
80
+ crl_validity_days: int = Field(
81
+ default=30, ge=1, le=365, description="CRL validity period in days"
82
+ )
83
+ auto_renewal: bool = Field(
84
+ default=False, description="Whether automatic certificate renewal is enabled"
85
+ )
86
+ renewal_threshold_days: int = Field(
87
+ default=30, ge=1, le=90, description="Days before expiry to renew"
88
+ )
89
+
90
+ @field_validator("hash_algorithm")
91
+ @classmethod
92
+ def validate_hash_algorithm(cls, v):
93
+ """Validate hash algorithm."""
94
+ valid_algorithms = ["sha1", "sha256", "sha384", "sha512"]
95
+ if v not in valid_algorithms:
96
+ raise ValueError(
97
+ f"Invalid hash algorithm. Must be one of: {valid_algorithms}"
98
+ )
99
+ return v
100
+
101
+ @model_validator(mode="after")
102
+ def validate_certificate_configuration(self):
103
+ """Validate certificate configuration consistency."""
104
+ if self.enabled:
105
+ # BUGFIX: Only require CA paths if not in CA creation mode
106
+ if not self.ca_creation_mode:
107
+ if not self.ca_cert_path or not self.ca_key_path:
108
+ raise ValueError(
109
+ "Certificate management enabled but CA certificate and key paths are required. "
110
+ "Set ca_creation_mode=True if you are creating a CA certificate."
111
+ )
112
+
113
+ if self.crl_enabled and not self.crl_path:
114
+ raise ValueError("CRL enabled but CRL path is required")
115
+
116
+ return self
117
+
118
+
119
+ def create_patch_file():
120
+ """Create a patch file for the mcp_security_framework."""
121
+
122
+ patch_content = '''--- a/mcp_security_framework/schemas/config.py
123
+ +++ b/mcp_security_framework/schemas/config.py
124
+ @@ -1,6 +1,7 @@
125
+ from typing import Optional
126
+ from pydantic import BaseModel, Field, field_validator, model_validator
127
+
128
+ +
129
+ class CertificateConfig(BaseModel):
130
+ """
131
+ Certificate Management Configuration Model
132
+ @@ -8,6 +9,7 @@ class CertificateConfig(BaseModel):
133
+ This model defines certificate management configuration settings
134
+ including CA settings, certificate storage, and validation options.
135
+
136
+ + BUGFIX: Added ca_creation_mode to allow CA certificate creation
137
+ Attributes:
138
+ enabled: Whether certificate management is enabled
139
+ ca_cert_path: Path to CA certificate
140
+ @@ -20,6 +22,9 @@ class CertificateConfig(BaseModel):
141
+ enabled: bool = Field(
142
+ default=False, description="Whether certificate management is enabled"
143
+ )
144
+ + ca_creation_mode: bool = Field(
145
+ + default=False, description="Whether we are in CA creation mode (bypasses CA path validation)"
146
+ + )
147
+ ca_cert_path: Optional[str] = Field(
148
+ default=None, description="Path to CA certificate"
149
+ )
150
+ @@ -60,7 +65,9 @@ class CertificateConfig(BaseModel):
151
+ @model_validator(mode="after")
152
+ def validate_certificate_configuration(self):
153
+ """Validate certificate configuration consistency."""
154
+ if self.enabled:
155
+ - if not self.ca_cert_path or not self.ca_key_path:
156
+ - raise ValueError(
157
+ - "Certificate management enabled but CA certificate and key paths are required"
158
+ - )
159
+ + # BUGFIX: Only require CA paths if not in CA creation mode
160
+ + if not self.ca_creation_mode:
161
+ + if not self.ca_cert_path or not self.ca_key_path:
162
+ + raise ValueError(
163
+ + "Certificate management enabled but CA certificate and key paths are required. "
164
+ + "Set ca_creation_mode=True if you are creating a CA certificate."
165
+ + )
166
+
167
+ if self.crl_enabled and not self.crl_path:
168
+ raise ValueError("CRL enabled but CRL path is required")
169
+
170
+ return self
171
+ '''
172
+
173
+ patch_file = Path("certificate_config_bugfix.patch")
174
+ with open(patch_file, 'w') as f:
175
+ f.write(patch_content)
176
+
177
+ print(f"✅ Patch file created: {patch_file}")
178
+ return patch_file
179
+
180
+
181
+ def test_fixed_config():
182
+ """Test the fixed configuration."""
183
+ print("🧪 Testing Fixed CertificateConfig")
184
+ print("=" * 50)
185
+
186
+ # Test 1: CA creation mode should work without CA paths
187
+ print("Test 1: CA creation mode")
188
+ try:
189
+ config1 = FixedCertificateConfig(
190
+ enabled=True,
191
+ ca_creation_mode=True,
192
+ cert_storage_path="./certs",
193
+ key_storage_path="./keys"
194
+ )
195
+ print("✅ CA creation mode works correctly")
196
+ except Exception as e:
197
+ print(f"❌ CA creation mode failed: {e}")
198
+ return False
199
+
200
+ # Test 2: Normal mode should require CA paths
201
+ print("Test 2: Normal mode without CA paths")
202
+ try:
203
+ config2 = FixedCertificateConfig(
204
+ enabled=True,
205
+ ca_creation_mode=False,
206
+ cert_storage_path="./certs",
207
+ key_storage_path="./keys"
208
+ )
209
+ print("❌ Normal mode should have failed without CA paths")
210
+ return False
211
+ except ValueError as e:
212
+ print("✅ Normal mode correctly requires CA paths")
213
+ except Exception as e:
214
+ print(f"❌ Unexpected error: {e}")
215
+ return False
216
+
217
+ # Test 3: Normal mode with CA paths should work
218
+ print("Test 3: Normal mode with CA paths")
219
+ try:
220
+ config3 = FixedCertificateConfig(
221
+ enabled=True,
222
+ ca_creation_mode=False,
223
+ ca_cert_path="./certs/ca.crt",
224
+ ca_key_path="./keys/ca.key",
225
+ cert_storage_path="./certs",
226
+ key_storage_path="./keys"
227
+ )
228
+ print("✅ Normal mode with CA paths works correctly")
229
+ except Exception as e:
230
+ print(f"❌ Normal mode with CA paths failed: {e}")
231
+ return False
232
+
233
+ print("\n🎉 All tests passed!")
234
+ return True
235
+
236
+
237
+ def main():
238
+ """Main entry point."""
239
+ print("🔧 mcp_security_framework CertificateConfig Bugfix")
240
+ print("=" * 60)
241
+ print()
242
+ print("ISSUE DESCRIPTION:")
243
+ print("CertificateConfig requires CA certificate and key paths even when")
244
+ print("creating a CA certificate. This creates a chicken-and-egg problem.")
245
+ print()
246
+ print("SOLUTION:")
247
+ print("Add ca_creation_mode field to bypass CA path validation when")
248
+ print("creating a CA certificate.")
249
+ print()
250
+
251
+ # Test the fix
252
+ if test_fixed_config():
253
+ # Create patch file
254
+ patch_file = create_patch_file()
255
+ print(f"\n📁 To apply this fix to mcp_security_framework:")
256
+ print(f" 1. Copy the patch file to the framework directory")
257
+ print(f" 2. Run: patch -p1 < {patch_file}")
258
+ print(f" 3. Or manually apply the changes shown in the patch")
259
+ print()
260
+ print("🔧 USAGE EXAMPLE:")
261
+ print(" # For CA creation:")
262
+ print(" config = CertificateConfig(")
263
+ print(" enabled=True,")
264
+ print(" ca_creation_mode=True, # <-- This is the fix")
265
+ print(" cert_storage_path='./certs',")
266
+ print(" key_storage_path='./keys'")
267
+ print(" )")
268
+ print()
269
+ print(" # For normal certificate creation:")
270
+ print(" config = CertificateConfig(")
271
+ print(" enabled=True,")
272
+ print(" ca_creation_mode=False,")
273
+ print(" ca_cert_path='./certs/ca.crt',")
274
+ print(" ca_key_path='./keys/ca.key'")
275
+ print(" )")
276
+ else:
277
+ print("❌ Tests failed!")
278
+ return 1
279
+
280
+ return 0
281
+
282
+
283
+ if __name__ == "__main__":
284
+ sys.exit(main())