amazon-ads-mcp 0.2.7__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 (82) hide show
  1. amazon_ads_mcp/__init__.py +11 -0
  2. amazon_ads_mcp/auth/__init__.py +33 -0
  3. amazon_ads_mcp/auth/base.py +211 -0
  4. amazon_ads_mcp/auth/hooks.py +172 -0
  5. amazon_ads_mcp/auth/manager.py +791 -0
  6. amazon_ads_mcp/auth/oauth_state_store.py +277 -0
  7. amazon_ads_mcp/auth/providers/__init__.py +14 -0
  8. amazon_ads_mcp/auth/providers/direct.py +393 -0
  9. amazon_ads_mcp/auth/providers/example_auth0.py.example +216 -0
  10. amazon_ads_mcp/auth/providers/openbridge.py +512 -0
  11. amazon_ads_mcp/auth/registry.py +146 -0
  12. amazon_ads_mcp/auth/secure_token_store.py +297 -0
  13. amazon_ads_mcp/auth/token_store.py +723 -0
  14. amazon_ads_mcp/config/__init__.py +5 -0
  15. amazon_ads_mcp/config/sampling.py +111 -0
  16. amazon_ads_mcp/config/settings.py +366 -0
  17. amazon_ads_mcp/exceptions.py +314 -0
  18. amazon_ads_mcp/middleware/__init__.py +11 -0
  19. amazon_ads_mcp/middleware/authentication.py +1474 -0
  20. amazon_ads_mcp/middleware/caching.py +177 -0
  21. amazon_ads_mcp/middleware/oauth.py +175 -0
  22. amazon_ads_mcp/middleware/sampling.py +112 -0
  23. amazon_ads_mcp/models/__init__.py +320 -0
  24. amazon_ads_mcp/models/amc_models.py +837 -0
  25. amazon_ads_mcp/models/api_responses.py +847 -0
  26. amazon_ads_mcp/models/base_models.py +215 -0
  27. amazon_ads_mcp/models/builtin_responses.py +496 -0
  28. amazon_ads_mcp/models/dsp_models.py +556 -0
  29. amazon_ads_mcp/models/stores_brands.py +610 -0
  30. amazon_ads_mcp/server/__init__.py +6 -0
  31. amazon_ads_mcp/server/__main__.py +6 -0
  32. amazon_ads_mcp/server/builtin_prompts.py +269 -0
  33. amazon_ads_mcp/server/builtin_tools.py +962 -0
  34. amazon_ads_mcp/server/file_routes.py +547 -0
  35. amazon_ads_mcp/server/html_templates.py +149 -0
  36. amazon_ads_mcp/server/mcp_server.py +327 -0
  37. amazon_ads_mcp/server/openapi_utils.py +158 -0
  38. amazon_ads_mcp/server/sampling_handler.py +251 -0
  39. amazon_ads_mcp/server/server_builder.py +751 -0
  40. amazon_ads_mcp/server/sidecar_loader.py +178 -0
  41. amazon_ads_mcp/server/transform_executor.py +827 -0
  42. amazon_ads_mcp/tools/__init__.py +22 -0
  43. amazon_ads_mcp/tools/cache_management.py +105 -0
  44. amazon_ads_mcp/tools/download_tools.py +267 -0
  45. amazon_ads_mcp/tools/identity.py +236 -0
  46. amazon_ads_mcp/tools/oauth.py +598 -0
  47. amazon_ads_mcp/tools/profile.py +150 -0
  48. amazon_ads_mcp/tools/profile_listing.py +285 -0
  49. amazon_ads_mcp/tools/region.py +320 -0
  50. amazon_ads_mcp/tools/region_identity.py +175 -0
  51. amazon_ads_mcp/utils/__init__.py +6 -0
  52. amazon_ads_mcp/utils/async_compat.py +215 -0
  53. amazon_ads_mcp/utils/errors.py +452 -0
  54. amazon_ads_mcp/utils/export_content_type_resolver.py +249 -0
  55. amazon_ads_mcp/utils/export_download_handler.py +579 -0
  56. amazon_ads_mcp/utils/header_resolver.py +81 -0
  57. amazon_ads_mcp/utils/http/__init__.py +56 -0
  58. amazon_ads_mcp/utils/http/circuit_breaker.py +127 -0
  59. amazon_ads_mcp/utils/http/client_manager.py +329 -0
  60. amazon_ads_mcp/utils/http/request.py +207 -0
  61. amazon_ads_mcp/utils/http/resilience.py +512 -0
  62. amazon_ads_mcp/utils/http/resilient_client.py +195 -0
  63. amazon_ads_mcp/utils/http/retry.py +76 -0
  64. amazon_ads_mcp/utils/http_client.py +873 -0
  65. amazon_ads_mcp/utils/media/__init__.py +21 -0
  66. amazon_ads_mcp/utils/media/negotiator.py +243 -0
  67. amazon_ads_mcp/utils/media/types.py +199 -0
  68. amazon_ads_mcp/utils/openapi/__init__.py +16 -0
  69. amazon_ads_mcp/utils/openapi/json.py +55 -0
  70. amazon_ads_mcp/utils/openapi/loader.py +263 -0
  71. amazon_ads_mcp/utils/openapi/refs.py +46 -0
  72. amazon_ads_mcp/utils/region_config.py +200 -0
  73. amazon_ads_mcp/utils/response_wrapper.py +171 -0
  74. amazon_ads_mcp/utils/sampling_helpers.py +156 -0
  75. amazon_ads_mcp/utils/sampling_wrapper.py +173 -0
  76. amazon_ads_mcp/utils/security.py +630 -0
  77. amazon_ads_mcp/utils/tool_naming.py +137 -0
  78. amazon_ads_mcp-0.2.7.dist-info/METADATA +664 -0
  79. amazon_ads_mcp-0.2.7.dist-info/RECORD +82 -0
  80. amazon_ads_mcp-0.2.7.dist-info/WHEEL +4 -0
  81. amazon_ads_mcp-0.2.7.dist-info/entry_points.txt +3 -0
  82. amazon_ads_mcp-0.2.7.dist-info/licenses/LICENSE +21 -0
@@ -0,0 +1,207 @@
1
+ """HTTP request utilities with response handling and retry logic.
2
+
3
+ This module provides a simplified interface for making HTTP requests
4
+ with automatic retry logic and convenient response handling. It
5
+ includes a wrapper class for HTTP responses that provides easy access
6
+ to common response properties and methods.
7
+
8
+ The module integrates with the HTTP client manager and retry decorator
9
+ to provide robust HTTP communication capabilities.
10
+ """
11
+
12
+ from typing import Any, Dict, Optional
13
+
14
+ import httpx
15
+
16
+ from .client_manager import get_http_client
17
+ from .retry import async_retry
18
+
19
+
20
+ class HTTPResponse:
21
+ """Wrapper for HTTP responses with convenient access methods.
22
+
23
+ This class wraps httpx.Response objects and provides easy access
24
+ to common response properties and methods. It includes caching
25
+ for JSON responses to avoid repeated parsing and provides
26
+ convenient boolean methods for checking response status.
27
+ """
28
+
29
+ def __init__(self, response: httpx.Response):
30
+ """Initialize the response wrapper.
31
+
32
+ :param response: The underlying httpx.Response object
33
+ :type response: httpx.Response
34
+ """
35
+ self.response = response
36
+ self._json_cache = None
37
+
38
+ @property
39
+ def status_code(self) -> int:
40
+ """Get the HTTP status code of the response.
41
+
42
+ :return: HTTP status code
43
+ :rtype: int
44
+ """
45
+ return self.response.status_code
46
+
47
+ @property
48
+ def headers(self) -> httpx.Headers:
49
+ """Get the response headers.
50
+
51
+ :return: Response headers
52
+ :rtype: httpx.Headers
53
+ """
54
+ return self.response.headers
55
+
56
+ @property
57
+ def text(self) -> str:
58
+ """Get the response body as text.
59
+
60
+ :return: Response body text
61
+ :rtype: str
62
+ """
63
+ return self.response.text
64
+
65
+ def json(self) -> Any:
66
+ """Get the response body as parsed JSON.
67
+
68
+ The result is cached to avoid repeated parsing of the same
69
+ response body.
70
+
71
+ :return: Parsed JSON response
72
+ :rtype: Any
73
+ """
74
+ if self._json_cache is None:
75
+ self._json_cache = self.response.json()
76
+ return self._json_cache
77
+
78
+ def is_success(self) -> bool:
79
+ """Check if the response indicates success (2xx status code).
80
+
81
+ :return: True if status code is in 200-299 range
82
+ :rtype: bool
83
+ """
84
+ return 200 <= self.status_code < 300
85
+
86
+ def is_client_error(self) -> bool:
87
+ """Check if the response indicates a client error (4xx status code).
88
+
89
+ :return: True if status code is in 400-499 range
90
+ :rtype: bool
91
+ """
92
+ return 400 <= self.status_code < 500
93
+
94
+ def is_server_error(self) -> bool:
95
+ """Check if the response indicates a server error (5xx status code).
96
+
97
+ :return: True if status code is in 500-599 range
98
+ :rtype: bool
99
+ """
100
+ return 500 <= self.status_code < 600
101
+
102
+
103
+ @async_retry(max_attempts=3, delay=1.0, backoff=2.0)
104
+ async def make_request(
105
+ method: str,
106
+ url: str,
107
+ headers: Optional[Dict[str, str]] = None,
108
+ json_data: Optional[Dict[str, Any]] = None,
109
+ params: Optional[Dict[str, Any]] = None,
110
+ timeout: Optional[float] = None,
111
+ **kwargs,
112
+ ) -> HTTPResponse:
113
+ """Make an HTTP request with automatic retry logic.
114
+
115
+ This function makes HTTP requests with configurable parameters
116
+ and automatic retry on failure. It uses the HTTP client manager
117
+ to get an appropriate client and applies retry logic for
118
+ transient failures.
119
+
120
+ :param method: HTTP method (e.g., 'GET', 'POST', 'PUT')
121
+ :type method: str
122
+ :param url: URL to make the request to
123
+ :type url: str
124
+ :param headers: Optional request headers
125
+ :type headers: Optional[Dict[str, str]]
126
+ :param json_data: Optional JSON data to send in request body
127
+ :type json_data: Optional[Dict[str, Any]]
128
+ :param params: Optional query parameters
129
+ :type params: Optional[Dict[str, Any]]
130
+ :param timeout: Optional request timeout in seconds
131
+ :type timeout: Optional[float]
132
+ :param **kwargs: Additional request parameters
133
+ :return: HTTPResponse wrapper containing the response
134
+ :rtype: HTTPResponse
135
+ :raises httpx.HTTPStatusError: If the response status indicates an error
136
+ """
137
+ client = await get_http_client()
138
+
139
+ request_kwargs = {"headers": headers, "params": params, **kwargs}
140
+ if json_data is not None:
141
+ request_kwargs["json"] = json_data
142
+ if timeout is not None:
143
+ request_kwargs["timeout"] = timeout
144
+
145
+ response = await client.request(method, url, **request_kwargs)
146
+ response.raise_for_status()
147
+ return HTTPResponse(response)
148
+
149
+
150
+ async def get(url: str, **kwargs) -> HTTPResponse:
151
+ """Make a GET request.
152
+
153
+ :param url: URL to make the GET request to
154
+ :type url: str
155
+ :param **kwargs: Additional request parameters
156
+ :return: HTTPResponse wrapper containing the response
157
+ :rtype: HTTPResponse
158
+ """
159
+ return await make_request("GET", url, **kwargs)
160
+
161
+
162
+ async def post(url: str, **kwargs) -> HTTPResponse:
163
+ """Make a POST request.
164
+
165
+ :param url: URL to make the POST request to
166
+ :type url: str
167
+ :param **kwargs: Additional request parameters
168
+ :return: HTTPResponse wrapper containing the response
169
+ :rtype: HTTPResponse
170
+ """
171
+ return await make_request("POST", url, **kwargs)
172
+
173
+
174
+ async def put(url: str, **kwargs) -> HTTPResponse:
175
+ """Make a PUT request.
176
+
177
+ :param url: URL to make the PUT request to
178
+ :type url: str
179
+ :param **kwargs: Additional request parameters
180
+ :return: HTTPResponse wrapper containing the response
181
+ :rtype: HTTPResponse
182
+ """
183
+ return await make_request("PUT", url, **kwargs)
184
+
185
+
186
+ async def delete(url: str, **kwargs) -> HTTPResponse:
187
+ """Make a DELETE request.
188
+
189
+ :param url: URL to make the DELETE request to
190
+ :type url: str
191
+ :param **kwargs: Additional request parameters
192
+ :return: HTTPResponse wrapper containing the response
193
+ :rtype: HTTPResponse
194
+ """
195
+ return await make_request("DELETE", url, **kwargs)
196
+
197
+
198
+ async def patch(url: str, **kwargs) -> HTTPResponse:
199
+ """Make a PATCH request.
200
+
201
+ :param url: URL to make the PATCH request to
202
+ :type url: str
203
+ :param **kwargs: Additional request parameters
204
+ :return: HTTPResponse wrapper containing the response
205
+ :rtype: HTTPResponse
206
+ """
207
+ return await make_request("PATCH", url, **kwargs)