rollgate 1.0.0__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.
@@ -0,0 +1,288 @@
1
+ Metadata-Version: 2.4
2
+ Name: rollgate
3
+ Version: 1.0.0
4
+ Summary: Python SDK for Rollgate feature flags
5
+ Project-URL: Homepage, https://rollgate.io
6
+ Project-URL: Documentation, https://rollgate.io/docs/sdk/python
7
+ Project-URL: Repository, https://github.com/thejord-it/rollgate
8
+ Author-email: Rollgate <hello@rollgate.io>
9
+ License-Expression: MIT
10
+ Keywords: feature-flags,feature-toggles,rollgate,sdk
11
+ Classifier: Development Status :: 5 - Production/Stable
12
+ Classifier: Intended Audience :: Developers
13
+ Classifier: License :: OSI Approved :: MIT License
14
+ Classifier: Operating System :: OS Independent
15
+ Classifier: Programming Language :: Python :: 3
16
+ Classifier: Programming Language :: Python :: 3.9
17
+ Classifier: Programming Language :: Python :: 3.10
18
+ Classifier: Programming Language :: Python :: 3.11
19
+ Classifier: Programming Language :: Python :: 3.12
20
+ Classifier: Programming Language :: Python :: 3.13
21
+ Classifier: Topic :: Software Development :: Libraries :: Python Modules
22
+ Classifier: Typing :: Typed
23
+ Requires-Python: >=3.9
24
+ Requires-Dist: httpx-sse>=0.4.0
25
+ Requires-Dist: httpx>=0.25.0
26
+ Provides-Extra: dev
27
+ Requires-Dist: mypy>=1.0.0; extra == 'dev'
28
+ Requires-Dist: pytest-asyncio>=0.21.0; extra == 'dev'
29
+ Requires-Dist: pytest-cov>=4.0.0; extra == 'dev'
30
+ Requires-Dist: pytest>=7.0.0; extra == 'dev'
31
+ Requires-Dist: respx>=0.20.0; extra == 'dev'
32
+ Requires-Dist: ruff>=0.1.0; extra == 'dev'
33
+ Description-Content-Type: text/markdown
34
+
35
+ # Rollgate Python SDK
36
+
37
+ [![CI](https://github.com/rollgate/sdks/actions/workflows/ci.yml/badge.svg)](https://github.com/rollgate/sdks/actions/workflows/ci.yml)
38
+ [![PyPI version](https://img.shields.io/pypi/v/rollgate.svg)](https://pypi.org/project/rollgate/)
39
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
40
+
41
+ Official Python SDK for [Rollgate](https://rollgate.io) - Feature flags made simple.
42
+
43
+ ## Requirements
44
+
45
+ - Python 3.9+
46
+ - httpx >= 0.25.0
47
+ - httpx-sse >= 0.4.0
48
+
49
+ ## Installation
50
+
51
+ ```bash
52
+ pip install rollgate
53
+ ```
54
+
55
+ ## Quick Start
56
+
57
+ ```python
58
+ import asyncio
59
+ from rollgate import RollgateClient, RollgateConfig, UserContext
60
+
61
+ async def main():
62
+ # Initialize client
63
+ config = RollgateConfig(api_key="your-api-key")
64
+ client = RollgateClient(config)
65
+
66
+ # Initialize and fetch flags
67
+ await client.init()
68
+
69
+ # Check if feature is enabled
70
+ if client.is_enabled("new-feature"):
71
+ print("New feature is enabled!")
72
+
73
+ # With user targeting
74
+ await client.identify(UserContext(
75
+ id="user-123",
76
+ email="user@example.com",
77
+ attributes={"plan": "pro", "country": "IT"}
78
+ ))
79
+
80
+ if client.is_enabled("premium-feature"):
81
+ print("Premium feature is enabled for this user!")
82
+
83
+ # Cleanup
84
+ await client.close()
85
+
86
+ asyncio.run(main())
87
+ ```
88
+
89
+ ## Context Manager
90
+
91
+ ```python
92
+ async with RollgateClient(RollgateConfig(api_key="your-api-key")) as client:
93
+ if client.is_enabled("my-feature"):
94
+ # Feature is enabled
95
+ pass
96
+ ```
97
+
98
+ ## Configuration
99
+
100
+ ```python
101
+ from rollgate import (
102
+ RollgateConfig,
103
+ RetryConfig,
104
+ CircuitBreakerConfig,
105
+ CacheConfig,
106
+ )
107
+
108
+ config = RollgateConfig(
109
+ api_key="your-api-key",
110
+ base_url="https://api.rollgate.io", # Custom API URL
111
+ refresh_interval_ms=30000, # Polling interval (30s default)
112
+ enable_streaming=False, # Use SSE for real-time updates
113
+ timeout_ms=5000, # Request timeout
114
+
115
+ # Retry configuration
116
+ retry=RetryConfig(
117
+ max_retries=3,
118
+ base_delay_ms=100,
119
+ max_delay_ms=10000,
120
+ jitter_factor=0.1,
121
+ ),
122
+
123
+ # Circuit breaker configuration
124
+ circuit_breaker=CircuitBreakerConfig(
125
+ failure_threshold=5,
126
+ recovery_timeout_ms=30000,
127
+ monitoring_window_ms=60000,
128
+ success_threshold=3,
129
+ ),
130
+
131
+ # Cache configuration
132
+ cache=CacheConfig(
133
+ ttl_ms=300000, # 5 minutes
134
+ stale_ttl_ms=3600000, # 1 hour
135
+ persist_path="/tmp/rollgate-cache.json", # Optional persistence
136
+ ),
137
+ )
138
+ ```
139
+
140
+ ## Events
141
+
142
+ ```python
143
+ client = RollgateClient(config)
144
+
145
+ # Register event callbacks
146
+ client.on("ready", lambda: print("Client ready"))
147
+ client.on("flags_updated", lambda flags: print(f"Flags updated: {flags}"))
148
+ client.on("flag_changed", lambda key, new, old: print(f"{key}: {old} -> {new}"))
149
+ client.on("error", lambda err: print(f"Error: {err}"))
150
+ client.on("circuit_open", lambda *args: print("Circuit breaker opened"))
151
+ client.on("circuit_closed", lambda: print("Circuit breaker closed"))
152
+
153
+ await client.init()
154
+ ```
155
+
156
+ ## Features
157
+
158
+ ### Polling (Default)
159
+
160
+ By default, the SDK polls for flag updates every 30 seconds.
161
+
162
+ ```python
163
+ config = RollgateConfig(
164
+ api_key="your-api-key",
165
+ refresh_interval_ms=30000, # Poll every 30s
166
+ )
167
+ ```
168
+
169
+ ### SSE Streaming
170
+
171
+ Enable Server-Sent Events for real-time flag updates:
172
+
173
+ ```python
174
+ config = RollgateConfig(
175
+ api_key="your-api-key",
176
+ enable_streaming=True,
177
+ )
178
+ ```
179
+
180
+ ### Circuit Breaker
181
+
182
+ The SDK includes a circuit breaker to prevent cascading failures:
183
+
184
+ ```python
185
+ # Check circuit state
186
+ state = client.circuit_state # CircuitState.CLOSED, OPEN, or HALF_OPEN
187
+
188
+ # Get statistics
189
+ stats = client.get_circuit_stats()
190
+
191
+ # Force reset
192
+ client.reset_circuit()
193
+ ```
194
+
195
+ ### Caching
196
+
197
+ Flags are cached locally with stale-while-revalidate support:
198
+
199
+ ```python
200
+ # Get cache statistics
201
+ stats = client.get_cache_stats()
202
+ hit_rate = client.get_cache_hit_rate()
203
+
204
+ # Clear cache
205
+ client.clear_cache()
206
+ ```
207
+
208
+ ### Error Handling
209
+
210
+ ```python
211
+ from rollgate import (
212
+ RollgateError,
213
+ AuthenticationError,
214
+ NetworkError,
215
+ RateLimitError,
216
+ )
217
+
218
+ try:
219
+ await client.init()
220
+ except AuthenticationError as e:
221
+ print(f"Invalid API key: {e}")
222
+ except NetworkError as e:
223
+ print(f"Network error: {e}")
224
+ except RateLimitError as e:
225
+ print(f"Rate limited, retry after: {e.retry_after}s")
226
+ except RollgateError as e:
227
+ print(f"Rollgate error: {e}")
228
+ ```
229
+
230
+ ## API Reference
231
+
232
+ ### RollgateClient
233
+
234
+ | Method | Description |
235
+ | --------------------------------------- | ---------------------------------- |
236
+ | `init(user?)` | Initialize client and fetch flags |
237
+ | `is_enabled(flag_key, default?)` | Check if flag is enabled |
238
+ | `is_enabled_detail(flag_key, default?)` | Check flag with evaluation reason |
239
+ | `get_all_flags()` | Get all flags as dictionary |
240
+ | `identify(user)` | Set user context and refresh flags |
241
+ | `reset()` | Clear user context |
242
+ | `refresh()` | Force refresh flags |
243
+ | `close()` | Cleanup resources |
244
+
245
+ ### Evaluation Reasons
246
+
247
+ Get detailed information about why a flag evaluated to a particular value:
248
+
249
+ ```python
250
+ detail = client.is_enabled_detail("my-flag", False)
251
+ print(detail.value) # bool
252
+ print(detail.reason.kind) # "OFF", "TARGET_MATCH", "RULE_MATCH", "FALLTHROUGH", "ERROR", "UNKNOWN"
253
+ ```
254
+
255
+ Reason kinds:
256
+
257
+ | Kind | Description |
258
+ | -------------- | ---------------------------------- |
259
+ | `OFF` | Flag is disabled |
260
+ | `TARGET_MATCH` | User is in the flag's target list |
261
+ | `RULE_MATCH` | User matched a targeting rule |
262
+ | `FALLTHROUGH` | Default rollout (no rules matched) |
263
+ | `ERROR` | Error during evaluation |
264
+ | `UNKNOWN` | Flag not found |
265
+
266
+ ### UserContext
267
+
268
+ | Field | Type | Description |
269
+ | ------------ | ------- | ------------------------------- |
270
+ | `id` | `str` | User identifier (required) |
271
+ | `email` | `str?` | User email |
272
+ | `attributes` | `dict?` | Custom attributes for targeting |
273
+
274
+ ## Documentation
275
+
276
+ - [Getting Started](../../docs/GETTING-STARTED.md)
277
+ - [Architecture](../../docs/ARCHITECTURE.md)
278
+ - [Production Setup](../../docs/PRODUCTION-SETUP.md)
279
+
280
+ Full documentation: [docs.rollgate.io](https://rollgate.io/docs)
281
+
282
+ ## About Rollgate
283
+
284
+ [Rollgate](https://rollgate.io) is a feature management platform that helps teams release features safely with gradual rollouts, user targeting, and instant kill switches.
285
+
286
+ ## License
287
+
288
+ MIT
@@ -0,0 +1,14 @@
1
+ rollgate/__init__.py,sha256=SyOLOjfZblOv3AtKLLr96eEjYGEfQpiHZUrH2g_dv9I,2970
2
+ rollgate/cache.py,sha256=XjjRrbOsnR9lRGE6HjYmstq5BtQLFhbx6P4A4XRSmto,7634
3
+ rollgate/circuit_breaker.py,sha256=RWQE0I90F1-0OHa1xDtenCez9P7kU2CYq8JjQCyJ1Q8,8121
4
+ rollgate/client.py,sha256=F1jwY_H8arx5Pf25KBk5zfZty3D0TZ8ssbXiAsJ-L0g,18434
5
+ rollgate/dedup.py,sha256=N2B1KhFVdLL9epdNGoaSq1hDreJK8Cz3ed6Cbo678dE,4969
6
+ rollgate/errors.py,sha256=C_Ib_mkCkttX6_7HlQ4S4EzigKiWqvTauGGeYFEFuEw,4267
7
+ rollgate/evaluate.py,sha256=J1vnZB9EqfXMUeNZ9QKDtjo8bxbrXsuANnnlkNZlGmQ,10619
8
+ rollgate/metrics.py,sha256=ByIyWeIL9Oc2YDkgIHQ2iq0xYRo4OTAY4nlvsdxOsGY,18911
9
+ rollgate/reasons.py,sha256=uL21HpKshQP87iI2CAmzETKAG5X5fIbMeuPIWRTrydQ,3963
10
+ rollgate/retry.py,sha256=L_pR8CbReBBNZ0Av6GydNB2EjKaXPdCbV0DggyWIptg,4448
11
+ rollgate/tracing.py,sha256=q4XgH8v0MGBnFxYEG4WElS3K9O53b3IlbFqPiQl49Yc,11697
12
+ rollgate-1.0.0.dist-info/METADATA,sha256=BfeAeu17uJWvunERFEnA4_IYFTfhTGNfRaCQFJz5CLc,8182
13
+ rollgate-1.0.0.dist-info/WHEEL,sha256=WLgqFyCfm_KASv4WHyYy0P3pM_m7J5L9k2skdKLirC8,87
14
+ rollgate-1.0.0.dist-info/RECORD,,
@@ -0,0 +1,4 @@
1
+ Wheel-Version: 1.0
2
+ Generator: hatchling 1.28.0
3
+ Root-Is-Purelib: true
4
+ Tag: py3-none-any