scrapely-python 0.1.35__tar.gz → 0.1.36__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 (71) hide show
  1. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/CHANGELOG.md +6 -0
  2. {scrapely_python-0.1.35/src/scrapely_python.egg-info → scrapely_python-0.1.36}/PKG-INFO +1 -1
  3. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/pyproject.toml +1 -1
  4. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/__init__.py +1 -1
  5. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/api_client.py +8 -6
  6. {scrapely_python-0.1.35 → scrapely_python-0.1.36/src/scrapely_python.egg-info}/PKG-INFO +1 -1
  7. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/LICENSE +0 -0
  8. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/LICENSE-APACHE +0 -0
  9. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/MANIFEST.in +0 -0
  10. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/NOTICE +0 -0
  11. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/README.md +0 -0
  12. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/setup.cfg +0 -0
  13. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/_browser_locations.py +0 -0
  14. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/actor.py +0 -0
  15. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/browser_configuration.py +0 -0
  16. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/cdp_retry.py +0 -0
  17. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/charging.py +0 -0
  18. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/charging_client.py +0 -0
  19. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/configuration.py +0 -0
  20. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/crypto/__init__.py +0 -0
  21. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/crypto/_secrets.py +0 -0
  22. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/errors.py +0 -0
  23. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/events/__init__.py +0 -0
  24. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/events/_types.py +0 -0
  25. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/events/event_manager.py +0 -0
  26. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/log.py +0 -0
  27. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/patch_browser_pool.py +0 -0
  28. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/pricing_types.py +0 -0
  29. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/proxy_configuration.py +0 -0
  30. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/py.typed +0 -0
  31. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/request_loaders/__init__.py +0 -0
  32. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/request_loaders/_scrapely_request_list.py +0 -0
  33. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/__init__.py +0 -0
  34. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/_actor_runner.py +0 -0
  35. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/_async_thread.py +0 -0
  36. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/_logging_config.py +0 -0
  37. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/_serialization.py +0 -0
  38. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/_warnings.py +0 -0
  39. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/extensions/__init__.py +0 -0
  40. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/extensions/_graceful_stop.py +0 -0
  41. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/extensions/_httpcache.py +0 -0
  42. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/middlewares/__init__.py +0 -0
  43. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/middlewares/apify_proxy.py +0 -0
  44. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/pipelines/__init__.py +0 -0
  45. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/pipelines/actor_dataset_push.py +0 -0
  46. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/requests.py +0 -0
  47. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/scheduler.py +0 -0
  48. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/scrapy/utils.py +0 -0
  49. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/solver.py +0 -0
  50. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/__init__.py +0 -0
  51. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/_file_system/__init__.py +0 -0
  52. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/_file_system/_key_value_store_client.py +0 -0
  53. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/_file_system/_storage_client.py +0 -0
  54. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/_metadata.py +0 -0
  55. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/client.py +0 -0
  56. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/patch_storage.py +0 -0
  57. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/scrapely_dataset_client.py +0 -0
  58. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/scrapely_kvs_client.py +0 -0
  59. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/scrapely_rq_client.py +0 -0
  60. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/scrapely_storage_client.py +0 -0
  61. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/smart_scrapely_storage_client.py +0 -0
  62. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/types.py +0 -0
  63. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage/utils.py +0 -0
  64. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storage_clients/__init__.py +0 -0
  65. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/storages/__init__.py +0 -0
  66. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/types.py +0 -0
  67. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely/webhook.py +0 -0
  68. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely_python.egg-info/SOURCES.txt +0 -0
  69. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely_python.egg-info/dependency_links.txt +0 -0
  70. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely_python.egg-info/requires.txt +0 -0
  71. {scrapely_python-0.1.35 → scrapely_python-0.1.36}/src/scrapely_python.egg-info/top_level.txt +0 -0
@@ -2,6 +2,12 @@
2
2
 
3
3
  All notable changes to this project will be documented in this file.
4
4
 
5
+ ## [Unreleased]
6
+
7
+ ## [0.1.36] - 2026-10-26
8
+
9
+ - Opening a named dataset, key-value store or request queue (`Actor.open_dataset('name')` and the like) retries when the API answers `503 storage-name-busy`. The API sends it when another request kept creating or renaming a storage of that name for over 15 s; nothing was changed, so the open is simply repeated. It used to fail the open.
10
+
5
11
  ## [0.1.35] - 2026-10-26
6
12
 
7
13
  - Once `Actor.fail()` has run, the run stays failed. A later `Actor.exit()` keeps the failure's exit code and status message, so the usual `try: ... await Actor.fail(...) finally: await Actor.exit()` pattern now ends the run as FAILED. Before, the `exit()` in `finally` replaced the failure's exit code 1 with 0 and the run ended as SUCCEEDED with the failure message as its status. The same holds after `fail()` whose `SystemExit` was caught, after `fail(ExitOptions(exit=False))` (also inside `async with Actor(...)` and `Actor.main()`), and for a second `fail()`, which keeps the first failure's code and message.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: scrapely-python
3
- Version: 0.1.35
3
+ Version: 0.1.36
4
4
  Summary: Scrapely Python SDK - A toolkit for building Actors on the Scrapely platform
5
5
  Author-email: Scrapely <support@scrape.ly>
6
6
  License-Expression: MIT AND Apache-2.0
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "scrapely-python"
7
- version = "0.1.35"
7
+ version = "0.1.36"
8
8
  description = "Scrapely Python SDK - A toolkit for building Actors on the Scrapely platform"
9
9
  readme = "README.md"
10
10
  license = "MIT AND Apache-2.0"
@@ -227,7 +227,7 @@ if TYPE_CHECKING: # Static analysers and IDEs see the lazy names as plain impor
227
227
  set_api_storage,
228
228
  )
229
229
 
230
- __version__ = '0.1.35'
230
+ __version__ = '0.1.36'
231
231
  __all__ = [
232
232
  # Core
233
233
  'Actor',
@@ -40,11 +40,13 @@ def is_retryable_response(
40
40
 
41
41
  429 always: the run API limiter and dataset backpressure refuse it before
42
42
  anything is written. Idempotent methods: also 500/502/503/504. Others
43
- (dataset push, KV PUT) only on a 503 that certainly was not processed: the
44
- rate limiter refused it ("rate-limit-unavailable", before the handler), or
45
- HAProxy had no backend (its own page, nothing forwarded). Any other 503 may
46
- mean "outcome unknown" (a direct dataset write whose commit was not
47
- confirmed), and re-sending could store the items twice.
43
+ (dataset push, KV PUT, named storage create) only on a 503 that certainly
44
+ was not processed: the rate limiter refused it ("rate-limit-unavailable",
45
+ before the handler), another request held the storage name
46
+ ("storage-name-busy", nothing changed), or HAProxy had no backend (its own
47
+ page, nothing forwarded). Any other 503 may mean "outcome unknown" (a
48
+ direct dataset write whose commit was not confirmed), and re-sending could
49
+ store the items twice.
48
50
  """
49
51
  if status == 429:
50
52
  return True
@@ -52,7 +54,7 @@ def is_retryable_response(
52
54
  return status in (500, 502, 503, 504)
53
55
  if status != 503:
54
56
  return False
55
- return error_type == 'rate-limit-unavailable' or NO_BACKEND_MARKER in (body_text or '')
57
+ return error_type in ('rate-limit-unavailable', 'storage-name-busy') or NO_BACKEND_MARKER in (body_text or '')
56
58
 
57
59
 
58
60
  def unwrap_data(value: Any) -> Any:
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: scrapely-python
3
- Version: 0.1.35
3
+ Version: 0.1.36
4
4
  Summary: Scrapely Python SDK - A toolkit for building Actors on the Scrapely platform
5
5
  Author-email: Scrapely <support@scrape.ly>
6
6
  License-Expression: MIT AND Apache-2.0