embed-client-dev 4.0.78__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.
Files changed (48) hide show
  1. embed_client/__init__.py +36 -0
  2. embed_client/__main__.py +15 -0
  3. embed_client/_version.py +3 -0
  4. embed_client/adapter_config_factory.py +213 -0
  5. embed_client/adapter_config_normalizer.py +135 -0
  6. embed_client/adapter_generator_bridge.py +166 -0
  7. embed_client/auth.py +189 -0
  8. embed_client/cli.py +483 -0
  9. embed_client/cli_core.py +427 -0
  10. embed_client/client_factory.py +515 -0
  11. embed_client/client_factory_examples.py +375 -0
  12. embed_client/client_factory_helpers.py +59 -0
  13. embed_client/config.py +408 -0
  14. embed_client/config_defaults.py +77 -0
  15. embed_client/config_examples.py +228 -0
  16. embed_client/config_generator.py +652 -0
  17. embed_client/config_generator_cli.py +151 -0
  18. embed_client/config_presets.py +245 -0
  19. embed_client/config_validator.py +246 -0
  20. embed_client/config_validator_cli.py +141 -0
  21. embed_client/constants.py +52 -0
  22. embed_client/demo_cli.py +78 -0
  23. embed_client/demo_security_cli.py +206 -0
  24. embed_client/embed_file_output_validate.py +348 -0
  25. embed_client/embed_file_status_store.py +80 -0
  26. embed_client/embedding_client.py +1929 -0
  27. embed_client/embedding_client_helpers.py +105 -0
  28. embed_client/example_async_usage.py +357 -0
  29. embed_client/example_async_usage_demo.py +282 -0
  30. embed_client/example_async_usage_ru.py +340 -0
  31. embed_client/example_async_usage_ru_demo.py +313 -0
  32. embed_client/exceptions.py +122 -0
  33. embed_client/identifier_types.py +56 -0
  34. embed_client/json_embed_file_preflight.py +128 -0
  35. embed_client/local_json_embed_file.py +73 -0
  36. embed_client/md_embed_file_prep.py +197 -0
  37. embed_client/response_normalizer.py +160 -0
  38. embed_client/response_parsers.py +219 -0
  39. embed_client/security_cli.py +200 -0
  40. embed_client/security_cli_core.py +227 -0
  41. embed_client/ssl_examples.py +278 -0
  42. embed_client/ssl_manager.py +141 -0
  43. embed_client_dev-4.0.78.dist-info/METADATA +155 -0
  44. embed_client_dev-4.0.78.dist-info/RECORD +48 -0
  45. embed_client_dev-4.0.78.dist-info/WHEEL +5 -0
  46. embed_client_dev-4.0.78.dist-info/entry_points.txt +4 -0
  47. embed_client_dev-4.0.78.dist-info/licenses/LICENSE +21 -0
  48. embed_client_dev-4.0.78.dist-info/top_level.txt +1 -0
@@ -0,0 +1,200 @@
1
+ #!/usr/bin/env python3
2
+ """Security CLI Application for Text Vectorization.
3
+
4
+ Author: Vasiliy Zdanovskiy
5
+ email: vasilyvz@gmail.com
6
+ """
7
+
8
+ import argparse
9
+ import asyncio
10
+ import sys
11
+
12
+ from embed_client.security_cli_core import (
13
+ SecurityCLI,
14
+ create_config_from_security_mode,
15
+ )
16
+
17
+ # Re-export for backward compatibility
18
+ __all__ = ["SecurityCLI", "create_config_from_security_mode", "main"]
19
+
20
+
21
+ async def main() -> int:
22
+ """Main CLI function for security-aware vectorization."""
23
+ parser = argparse.ArgumentParser(
24
+ description="Security CLI Application for Text Vectorization",
25
+ formatter_class=argparse.RawDescriptionHelpFormatter,
26
+ epilog="""
27
+ Security Modes:
28
+ http - Plain HTTP without authentication
29
+ http_token - HTTP with API Key authentication
30
+ http_token_roles - HTTP with API Key and role-based access control
31
+ https - HTTPS with server certificate verification
32
+ https_token - HTTPS with server certificates + authentication
33
+ https_token_roles - HTTPS with server certificates + authentication + roles
34
+ mtls - Mutual TLS with client and server certificates
35
+ mtls_roles - mTLS with role-based access control
36
+
37
+ Examples:
38
+ # HTTP without authentication
39
+ python -m embed_client.security_cli vectorize --mode http "hello world"
40
+
41
+ # HTTP with token authentication
42
+ python -m embed_client.security_cli vectorize --mode http_token --api-key your-key "hello world"
43
+
44
+ # HTTPS with server certificates
45
+ python -m embed_client.security_cli vectorize --mode https \
46
+ --cert-file server.crt --key-file server.key "hello world"
47
+
48
+ # mTLS with client certificates
49
+ python -m embed_client.security_cli vectorize --mode mtls \
50
+ --cert-file client.crt --key-file client.key --ca-cert-file ca.crt "hello world"
51
+
52
+ # mTLS with roles
53
+ python -m embed_client.security_cli vectorize --mode mtls_roles \
54
+ --cert-file client.crt --key-file client.key --ca-cert-file ca.crt "hello world"
55
+ """,
56
+ )
57
+
58
+ parser.add_argument(
59
+ "--mode",
60
+ choices=[
61
+ "http",
62
+ "http_token",
63
+ "http_token_roles",
64
+ "https",
65
+ "https_token",
66
+ "https_token_roles",
67
+ "mtls",
68
+ "mtls_roles",
69
+ ],
70
+ required=True,
71
+ help="Security mode to use",
72
+ )
73
+
74
+ parser.add_argument(
75
+ "--host", default="localhost", help="Server host (default: localhost)"
76
+ )
77
+ parser.add_argument(
78
+ "--port", type=int, default=8001, help="Server port (default: 8001)"
79
+ )
80
+
81
+ parser.add_argument(
82
+ "--api-key", help="API key for authentication (required for token modes)"
83
+ )
84
+
85
+ parser.add_argument(
86
+ "--cert-file", help="Certificate file (required for HTTPS/mTLS modes)"
87
+ )
88
+ parser.add_argument(
89
+ "--key-file", help="Private key file (required for HTTPS/mTLS modes)"
90
+ )
91
+ parser.add_argument(
92
+ "--ca-cert-file", help="CA certificate file (required for mTLS modes)"
93
+ )
94
+
95
+ parser.add_argument(
96
+ "--format",
97
+ choices=["json", "csv", "vectors"],
98
+ default="json",
99
+ help="Output format",
100
+ )
101
+ parser.add_argument("--output", "-o", help="Output file (default: stdout)")
102
+
103
+ subparsers = parser.add_subparsers(dest="command", help="Available commands")
104
+
105
+ vectorize_parser = subparsers.add_parser("vectorize", help="Vectorize text")
106
+ vectorize_parser.add_argument("texts", nargs="*", help="Texts to vectorize")
107
+ vectorize_parser.add_argument(
108
+ "--file", "-f", help="File containing texts (one per line)"
109
+ )
110
+
111
+ subparsers.add_parser("health", help="Check service health")
112
+
113
+ help_parser = subparsers.add_parser("help", help="Get help from service")
114
+ help_parser.add_argument("--command", help="Specific command to get help for")
115
+
116
+ subparsers.add_parser("commands", help="Get available commands")
117
+
118
+ args = parser.parse_args()
119
+
120
+ if not args.command:
121
+ parser.print_help()
122
+ return 1
123
+
124
+ if "token" in args.mode and not args.api_key:
125
+ print("āŒ API key required for token-based authentication modes")
126
+ return 1
127
+
128
+ if "https" in args.mode or "mtls" in args.mode:
129
+ if not args.cert_file or not args.key_file:
130
+ print("āŒ Certificate and key files required for HTTPS/mTLS modes")
131
+ return 1
132
+
133
+ if "mtls" in args.mode and not args.ca_cert_file:
134
+ print("āŒ CA certificate file required for mTLS modes")
135
+ return 1
136
+
137
+ config = create_config_from_security_mode(
138
+ args.mode,
139
+ args.host,
140
+ args.port,
141
+ api_key=args.api_key,
142
+ cert_file=args.cert_file,
143
+ key_file=args.key_file,
144
+ ca_cert_file=args.ca_cert_file,
145
+ )
146
+
147
+ cli = SecurityCLI()
148
+
149
+ try:
150
+ print(f"šŸ”Œ Connecting using {args.mode} mode...")
151
+ if not await cli.connect(config):
152
+ return 1
153
+
154
+ if args.command == "vectorize":
155
+ texts = list(args.texts)
156
+ if args.file:
157
+ # Use async file reading to avoid blocking the event loop
158
+ loop = asyncio.get_event_loop()
159
+
160
+ def read_file_sync(file_path: str) -> list[str]:
161
+ """Read file synchronously in executor."""
162
+ with open(file_path, "r", encoding="utf-8") as f:
163
+ return [line.strip() for line in f if line.strip()]
164
+
165
+ file_texts = await loop.run_in_executor(None, read_file_sync, args.file)
166
+ texts.extend(file_texts)
167
+
168
+ if not texts:
169
+ print("āŒ No texts provided")
170
+ return 1
171
+
172
+ print(f"šŸ”¤ Vectorizing {len(texts)} texts using {args.mode} mode...")
173
+ await cli.vectorize_texts(texts, args.format)
174
+
175
+ elif args.command == "health":
176
+ print(f"šŸ„ Checking service health using {args.mode} mode...")
177
+ await cli.health_check()
178
+
179
+ elif args.command == "help":
180
+ print(f"ā“ Getting help using {args.mode} mode...")
181
+ await cli.get_help(args.command)
182
+
183
+ elif args.command == "commands":
184
+ print(f"šŸ“‹ Getting commands using {args.mode} mode...")
185
+ await cli.get_commands()
186
+
187
+ return 0
188
+
189
+ except KeyboardInterrupt:
190
+ print("\nšŸ›‘ Interrupted by user")
191
+ return 1
192
+ except Exception as exc: # noqa: BLE001
193
+ print(f"āŒ Error: {exc}")
194
+ return 1
195
+ finally:
196
+ await cli.disconnect()
197
+
198
+
199
+ if __name__ == "__main__": # pragma: no cover - CLI entry point
200
+ sys.exit(asyncio.run(main()))
@@ -0,0 +1,227 @@
1
+ """
2
+ Core components for Security CLI (client + config helpers).
3
+
4
+ Author: Vasiliy Zdanovskiy
5
+ email: vasilyvz@gmail.com
6
+ """
7
+
8
+ from __future__ import annotations
9
+
10
+ import json
11
+ from typing import Any, Dict, List, Optional
12
+
13
+ from embed_client.embedding_client import EmbeddingClient
14
+ from embed_client.response_parsers import extract_embeddings
15
+
16
+
17
+ class SecurityCLI:
18
+ """CLI application supporting all 8 security modes."""
19
+
20
+ def __init__(self) -> None:
21
+ self.client: Optional[EmbeddingClient] = None
22
+
23
+ async def connect(self, config: Dict[str, Any]) -> bool:
24
+ """Connect to embedding service using provided configuration."""
25
+ try:
26
+ from embed_client.embedding_client import embedding_client_from_config_dict
27
+
28
+ self.client = embedding_client_from_config_dict(config)
29
+ await self.client.__aenter__()
30
+ return True
31
+ except Exception as exc: # noqa: BLE001
32
+ print(f"āŒ Failed to connect: {exc}")
33
+ return False
34
+
35
+ async def disconnect(self) -> None:
36
+ """Disconnect from embedding service."""
37
+ if self.client:
38
+ await self.client.__aexit__(None, None, None)
39
+
40
+ async def health_check(self) -> bool:
41
+ """Check service health."""
42
+ if not self.client:
43
+ print("āŒ Client is not connected")
44
+ return False
45
+ try:
46
+ result = await self.client.health()
47
+ print(f"āœ… Service health: {result.get('status', 'unknown')}")
48
+ return True
49
+ except Exception as exc: # noqa: BLE001
50
+ print(f"āŒ Health check failed: {exc}")
51
+ return False
52
+
53
+ async def vectorize_texts(
54
+ self,
55
+ texts: List[str],
56
+ output_format: str = "json",
57
+ ) -> Optional[List[List[float]]]:
58
+ """Vectorize texts and print them in the requested format."""
59
+ if not self.client:
60
+ print("āŒ Client is not connected")
61
+ return None
62
+ try:
63
+ params: Dict[str, Any] = {"texts": texts}
64
+ result = await self.client.cmd("embed", params=params)
65
+
66
+ embeddings = extract_embeddings(result)
67
+
68
+ if output_format == "json":
69
+ print(json.dumps(embeddings, indent=2))
70
+ elif output_format == "csv":
71
+ self._print_csv(embeddings)
72
+ elif output_format == "vectors":
73
+ self._print_vectors(embeddings)
74
+
75
+ return embeddings
76
+ except Exception as exc: # noqa: BLE001
77
+ print(f"āŒ Vectorization failed: {exc}")
78
+ return None
79
+
80
+ async def get_help(self, command: Optional[str] = None) -> None:
81
+ """Get help information from the service."""
82
+ if not self.client:
83
+ print("āŒ Client is not connected")
84
+ return
85
+ try:
86
+ if command:
87
+ result = await self.client.cmd("help", params={"command": command})
88
+ else:
89
+ result = await self.client.cmd("help")
90
+ print(json.dumps(result, indent=2))
91
+ except Exception as exc: # noqa: BLE001
92
+ print(f"āŒ Help request failed: {exc}")
93
+
94
+ async def get_commands(self) -> None:
95
+ """Get available commands from the service."""
96
+ if not self.client:
97
+ print("āŒ Client is not connected")
98
+ return
99
+ try:
100
+ result = await self.client.list_commands()
101
+ print(json.dumps(result, indent=2))
102
+ except Exception as exc: # noqa: BLE001
103
+ print(f"āŒ Commands request failed: {exc}")
104
+
105
+ def _print_csv(self, embeddings: List[List[float]]) -> None:
106
+ """Print embeddings in CSV format."""
107
+ for index, embedding in enumerate(embeddings):
108
+ print(f"text_{index}," + ",".join(map(str, embedding)))
109
+
110
+ def _print_vectors(self, embeddings: List[List[float]]) -> None:
111
+ """Print embeddings as vectors."""
112
+ for index, embedding in enumerate(embeddings):
113
+ print(f"Text {index}: [{', '.join(map(str, embedding))}]")
114
+
115
+
116
+ def create_config_from_security_mode(
117
+ security_mode: str,
118
+ host: str,
119
+ port: int,
120
+ **kwargs: Any,
121
+ ) -> Dict[str, Any]:
122
+ """Create configuration dictionary based on security mode."""
123
+
124
+ config: Dict[str, Any] = {
125
+ "server": {"host": host, "port": port},
126
+ "auth": {"method": "none"},
127
+ "ssl": {"enabled": False},
128
+ "security": {"enabled": False},
129
+ }
130
+
131
+ if security_mode == "http":
132
+ config["server"]["host"] = f"http://{host.split('://')[-1]}"
133
+
134
+ elif security_mode == "http_token":
135
+ config["server"]["host"] = f"http://{host.split('://')[-1]}"
136
+ config["auth"]["method"] = "api_key"
137
+ config["security"] = {
138
+ "enabled": True,
139
+ "tokens": {"user": kwargs.get("api_key", "admin-secret-key")},
140
+ }
141
+
142
+ elif security_mode == "http_token_roles":
143
+ config["server"]["host"] = f"http://{host.split('://')[-1]}"
144
+ config["auth"]["method"] = "api_key"
145
+ config["security"] = {
146
+ "enabled": True,
147
+ "tokens": {"user": kwargs.get("api_key", "admin-secret-key")},
148
+ "roles": {
149
+ "admin": ["read", "write", "delete", "admin"],
150
+ "user": ["read", "write"],
151
+ "readonly": ["read"],
152
+ },
153
+ }
154
+
155
+ elif security_mode == "https":
156
+ config["server"]["host"] = f"https://{host.split('://')[-1]}"
157
+ config["ssl"] = {
158
+ "enabled": True,
159
+ "verify": False,
160
+ "cert_file": kwargs.get("cert_file"),
161
+ "key_file": kwargs.get("key_file"),
162
+ "ca_cert_file": kwargs.get("ca_cert_file"),
163
+ }
164
+
165
+ elif security_mode == "https_token":
166
+ config["server"]["host"] = f"https://{host.split('://')[-1]}"
167
+ config["auth"]["method"] = "api_key"
168
+ config["ssl"] = {
169
+ "enabled": True,
170
+ "cert_file": kwargs.get("cert_file"),
171
+ "key_file": kwargs.get("key_file"),
172
+ }
173
+ config["security"] = {
174
+ "enabled": True,
175
+ "tokens": {"user": kwargs.get("api_key", "admin-secret-key")},
176
+ }
177
+
178
+ elif security_mode == "https_token_roles":
179
+ config["server"]["host"] = f"https://{host.split('://')[-1]}"
180
+ config["auth"]["method"] = "api_key"
181
+ config["ssl"] = {
182
+ "enabled": True,
183
+ "cert_file": kwargs.get("cert_file"),
184
+ "key_file": kwargs.get("key_file"),
185
+ }
186
+ config["security"] = {
187
+ "enabled": True,
188
+ "tokens": {"user": kwargs.get("api_key", "admin-secret-key")},
189
+ "roles": {
190
+ "admin": ["read", "write", "delete", "admin"],
191
+ "user": ["read", "write"],
192
+ "readonly": ["read"],
193
+ },
194
+ }
195
+
196
+ elif security_mode == "mtls":
197
+ config["server"]["host"] = f"https://{host.split('://')[-1]}"
198
+ config["auth"]["method"] = "certificate"
199
+ config["ssl"] = {
200
+ "enabled": True,
201
+ "cert_file": kwargs.get("cert_file"),
202
+ "key_file": kwargs.get("key_file"),
203
+ "ca_cert_file": kwargs.get("ca_cert_file"),
204
+ }
205
+
206
+ elif security_mode == "mtls_roles":
207
+ config["server"]["host"] = f"https://{host.split('://')[-1]}"
208
+ config["auth"]["method"] = "certificate"
209
+ config["ssl"] = {
210
+ "enabled": True,
211
+ "cert_file": kwargs.get("cert_file"),
212
+ "key_file": kwargs.get("key_file"),
213
+ "ca_cert_file": kwargs.get("ca_cert_file"),
214
+ }
215
+ config["security"] = {
216
+ "enabled": True,
217
+ "roles": {
218
+ "admin": ["read", "write", "delete", "admin"],
219
+ "user": ["read", "write"],
220
+ "readonly": ["read"],
221
+ },
222
+ }
223
+
224
+ return config
225
+
226
+
227
+ __all__ = ["SecurityCLI", "create_config_from_security_mode"]
@@ -0,0 +1,278 @@
1
+ """
2
+ SSL/TLS examples for embed-client.
3
+
4
+ This module provides examples of how to use the SSL/TLS manager
5
+ with different security modes and configurations.
6
+
7
+ Author: Vasiliy Zdanovskiy
8
+ email: vasilyvz@gmail.com
9
+ """
10
+
11
+ from typing import Dict, Any
12
+ from embed_client.ssl_manager import create_ssl_manager
13
+
14
+
15
+ def get_http_config() -> Dict[str, Any]:
16
+ """
17
+ Get example configuration for HTTP (no SSL).
18
+
19
+ Returns:
20
+ Configuration dictionary for HTTP
21
+ """
22
+ return {"ssl": {"enabled": False}}
23
+
24
+
25
+ def get_https_config() -> Dict[str, Any]:
26
+ """
27
+ Get example configuration for HTTPS.
28
+
29
+ Returns:
30
+ Configuration dictionary for HTTPS
31
+ """
32
+ return {
33
+ "ssl": {
34
+ "enabled": True,
35
+ "verify_mode": "CERT_REQUIRED",
36
+ "check_hostname": True,
37
+ "check_expiry": True,
38
+ }
39
+ }
40
+
41
+
42
+ def get_https_with_ca_config() -> Dict[str, Any]:
43
+ """
44
+ Get example configuration for HTTPS with custom CA.
45
+
46
+ Returns:
47
+ Configuration dictionary for HTTPS with CA
48
+ """
49
+ return {
50
+ "ssl": {
51
+ "enabled": True,
52
+ "verify_mode": "CERT_REQUIRED",
53
+ "check_hostname": True,
54
+ "check_expiry": True,
55
+ "ca_cert_file": "certs/ca.crt",
56
+ }
57
+ }
58
+
59
+
60
+ def get_mtls_config() -> Dict[str, Any]:
61
+ """
62
+ Get example configuration for mTLS (mutual TLS).
63
+
64
+ Returns:
65
+ Configuration dictionary for mTLS
66
+ """
67
+ return {
68
+ "ssl": {
69
+ "enabled": True,
70
+ "verify_mode": "CERT_REQUIRED",
71
+ "check_hostname": True,
72
+ "check_expiry": True,
73
+ "cert_file": "certs/client.crt",
74
+ "key_file": "keys/client.key",
75
+ "ca_cert_file": "certs/ca.crt",
76
+ }
77
+ }
78
+
79
+
80
+ def get_mtls_no_verify_config() -> Dict[str, Any]:
81
+ """
82
+ Get example configuration for mTLS without verification.
83
+
84
+ Returns:
85
+ Configuration dictionary for mTLS without verification
86
+ """
87
+ return {
88
+ "ssl": {
89
+ "enabled": True,
90
+ "verify_mode": "CERT_NONE",
91
+ "check_hostname": False,
92
+ "check_expiry": False,
93
+ "cert_file": "certs/client.crt",
94
+ "key_file": "keys/client.key",
95
+ }
96
+ }
97
+
98
+
99
+ def demo_http_ssl():
100
+ """Demonstrate HTTP SSL configuration (disabled)."""
101
+ print("=== HTTP SSL Configuration Demo ===")
102
+
103
+ config = get_http_config()
104
+ ssl_manager = create_ssl_manager(config)
105
+
106
+ print(f"SSL enabled: {ssl_manager.is_ssl_enabled()}")
107
+ print(f"mTLS enabled: {ssl_manager.is_mtls_enabled()}")
108
+
109
+ # Note: SSL context and connector are created automatically by adapter
110
+ print("Note: SSL/TLS is handled automatically by mcp_proxy_adapter JsonRpcClient")
111
+
112
+ # Validate configuration
113
+ errors = ssl_manager.validate_ssl_config()
114
+ print(f"Validation errors: {errors}")
115
+
116
+
117
+ def demo_https_ssl():
118
+ """Demonstrate HTTPS SSL configuration."""
119
+ print("\n=== HTTPS SSL Configuration Demo ===")
120
+
121
+ config = get_https_config()
122
+ ssl_manager = create_ssl_manager(config)
123
+
124
+ print(f"SSL enabled: {ssl_manager.is_ssl_enabled()}")
125
+ print(f"mTLS enabled: {ssl_manager.is_mtls_enabled()}")
126
+
127
+ # Note: SSL context and connector are created automatically by adapter
128
+ print("Note: SSL/TLS is handled automatically by mcp_proxy_adapter JsonRpcClient")
129
+
130
+ # Get supported protocols
131
+ protocols = ssl_manager.get_supported_protocols()
132
+ print(f"Supported protocols: {protocols}")
133
+
134
+ # Validate configuration
135
+ errors = ssl_manager.validate_ssl_config()
136
+ print(f"Validation errors: {errors}")
137
+
138
+
139
+ def demo_https_with_ca_ssl():
140
+ """Demonstrate HTTPS SSL configuration with custom CA."""
141
+ print("\n=== HTTPS with CA SSL Configuration Demo ===")
142
+
143
+ config = get_https_with_ca_config()
144
+ ssl_manager = create_ssl_manager(config)
145
+
146
+ print(f"SSL enabled: {ssl_manager.is_ssl_enabled()}")
147
+ print(f"mTLS enabled: {ssl_manager.is_mtls_enabled()}")
148
+
149
+ # Note: SSL context is created automatically by adapter
150
+ print("Note: SSL/TLS is handled automatically by mcp_proxy_adapter JsonRpcClient")
151
+
152
+ # Validate configuration
153
+ errors = ssl_manager.validate_ssl_config()
154
+ print(f"Validation errors: {errors}")
155
+
156
+
157
+ def demo_mtls_ssl():
158
+ """Demonstrate mTLS SSL configuration."""
159
+ print("\n=== mTLS SSL Configuration Demo ===")
160
+
161
+ config = get_mtls_config()
162
+ ssl_manager = create_ssl_manager(config)
163
+
164
+ print(f"SSL enabled: {ssl_manager.is_ssl_enabled()}")
165
+ print(f"mTLS enabled: {ssl_manager.is_mtls_enabled()}")
166
+
167
+ # Note: SSL context is created automatically by adapter
168
+ print("Note: SSL/TLS is handled automatically by mcp_proxy_adapter JsonRpcClient")
169
+
170
+ # Validate configuration
171
+ errors = ssl_manager.validate_ssl_config()
172
+ print(f"Validation errors: {errors}")
173
+
174
+
175
+ def demo_mtls_no_verify_ssl():
176
+ """Demonstrate mTLS SSL configuration without verification."""
177
+ print("\n=== mTLS without Verification SSL Configuration Demo ===")
178
+
179
+ config = get_mtls_no_verify_config()
180
+ ssl_manager = create_ssl_manager(config)
181
+
182
+ print(f"SSL enabled: {ssl_manager.is_ssl_enabled()}")
183
+ print(f"mTLS enabled: {ssl_manager.is_mtls_enabled()}")
184
+
185
+ # Note: SSL context is created automatically by adapter
186
+ print("Note: SSL/TLS is handled automatically by mcp_proxy_adapter JsonRpcClient")
187
+
188
+ # Validate configuration
189
+ errors = ssl_manager.validate_ssl_config()
190
+ print(f"Validation errors: {errors}")
191
+
192
+
193
+ def demo_certificate_validation():
194
+ """Demonstrate certificate validation."""
195
+ print("\n=== Certificate Validation Demo ===")
196
+
197
+ config = {"ssl": {"enabled": True}}
198
+ ssl_manager = create_ssl_manager(config) # noqa: F841
199
+
200
+ # Note: Certificate validation is handled by mcp_security_framework
201
+ print("Note: Certificate validation is handled by mcp_security_framework")
202
+ print("Use validate_ssl_config() for configuration validation")
203
+
204
+
205
+ def demo_ssl_context_creation():
206
+ """Demonstrate SSL context creation using factory functions."""
207
+ print("\n=== SSL Context Creation Demo ===")
208
+ print(
209
+ "Note: SSL context creation is handled automatically by mcp_proxy_adapter JsonRpcClient"
210
+ )
211
+ print(
212
+ "No manual SSL context creation is needed - adapter handles all SSL/TLS operations"
213
+ )
214
+
215
+
216
+ def demo_connector_creation():
217
+ """Demonstrate connector creation using factory functions."""
218
+ print("\n=== Connector Creation Demo ===")
219
+ print(
220
+ "Note: Connector creation is handled automatically by mcp_proxy_adapter JsonRpcClient"
221
+ )
222
+ print(
223
+ "No manual connector creation is needed - adapter handles all transport operations"
224
+ )
225
+
226
+
227
+ def demo_ssl_configuration_validation():
228
+ """Demonstrate SSL configuration validation."""
229
+ print("\n=== SSL Configuration Validation Demo ===")
230
+
231
+ # Valid configuration
232
+ config = get_http_config()
233
+ ssl_manager = create_ssl_manager(config)
234
+ errors = ssl_manager.validate_ssl_config()
235
+ print(f"Valid config errors: {errors}")
236
+
237
+ # Invalid configuration (missing files)
238
+ config = get_mtls_config()
239
+ ssl_manager = create_ssl_manager(config)
240
+ errors = ssl_manager.validate_ssl_config()
241
+ print(f"Invalid config errors: {errors}")
242
+
243
+
244
+ def demo_ssl_capabilities():
245
+ """Demonstrate SSL capabilities detection."""
246
+ print("\n=== SSL Capabilities Demo ===")
247
+
248
+ config = {"ssl": {"enabled": True}}
249
+ ssl_manager = create_ssl_manager(config)
250
+
251
+ protocols = ssl_manager.get_supported_protocols()
252
+ print(f"Supported protocols: {protocols}")
253
+
254
+ ssl_config = ssl_manager.get_ssl_config()
255
+ print(f"SSL configuration: {ssl_config}")
256
+
257
+
258
+ def run_all_demos():
259
+ """Run all SSL/TLS demos."""
260
+ print("šŸ”’ SSL/TLS Manager Examples")
261
+ print("=" * 50)
262
+
263
+ demo_http_ssl()
264
+ demo_https_ssl()
265
+ demo_https_with_ca_ssl()
266
+ demo_mtls_ssl()
267
+ demo_mtls_no_verify_ssl()
268
+ demo_certificate_validation()
269
+ demo_ssl_configuration_validation()
270
+ demo_ssl_capabilities()
271
+ demo_ssl_context_creation()
272
+ demo_connector_creation()
273
+
274
+ print("\nāœ… All SSL/TLS demos completed!")
275
+
276
+
277
+ if __name__ == "__main__":
278
+ run_all_demos()