getanyapi 0.61.2__tar.gz → 0.63.0__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 (106) hide show
  1. {getanyapi-0.61.2 → getanyapi-0.63.0}/PKG-INFO +4 -3
  2. {getanyapi-0.61.2 → getanyapi-0.63.0}/README.md +3 -2
  3. {getanyapi-0.61.2 → getanyapi-0.63.0}/pyproject.toml +1 -1
  4. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/__init__.py +1 -1
  5. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/maps.py +2 -2
  6. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/zillow.py +118 -0
  7. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/types.py +5 -6
  8. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_account.py +18 -13
  9. {getanyapi-0.61.2 → getanyapi-0.63.0}/.gitignore +0 -0
  10. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/_account.py +0 -0
  11. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/_async_client.py +0 -0
  12. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/_client.py +0 -0
  13. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/_errors.py +0 -0
  14. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/_idempotency.py +0 -0
  15. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/_pagination.py +0 -0
  16. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/_transport.py +0 -0
  17. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/discovery_types.py +0 -0
  18. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/__init__.py +0 -0
  19. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/ahrefs.py +0 -0
  20. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/airbnb.py +0 -0
  21. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/alibaba.py +0 -0
  22. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/amazon.py +0 -0
  23. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/apollo.py +0 -0
  24. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/appstore.py +0 -0
  25. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/bluesky.py +0 -0
  26. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/booking.py +0 -0
  27. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/capterra.py +0 -0
  28. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/chatgpt.py +0 -0
  29. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/coinmarketcap.py +0 -0
  30. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/company.py +0 -0
  31. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/company_enrichment.py +0 -0
  32. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/company_identify.py +0 -0
  33. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/company_search.py +0 -0
  34. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/congress.py +0 -0
  35. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/contact_enrichment.py +0 -0
  36. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/douyin.py +0 -0
  37. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/ebay.py +0 -0
  38. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/email.py +0 -0
  39. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/email_finding.py +0 -0
  40. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/email_verification.py +0 -0
  41. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/facebook.py +0 -0
  42. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/fiverr.py +0 -0
  43. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/g2.py +0 -0
  44. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/gemini.py +0 -0
  45. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/github.py +0 -0
  46. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/glassdoor.py +0 -0
  47. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/google.py +0 -0
  48. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/google_ads.py +0 -0
  49. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/google_finance.py +0 -0
  50. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/google_shopping.py +0 -0
  51. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/hackernews.py +0 -0
  52. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/indeed.py +0 -0
  53. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/instagram.py +0 -0
  54. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/job_search.py +0 -0
  55. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/linkedin.py +0 -0
  56. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/mobile_phone.py +0 -0
  57. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/naver.py +0 -0
  58. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/nextdoor.py +0 -0
  59. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/people_search.py +0 -0
  60. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/perplexity.py +0 -0
  61. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/person.py +0 -0
  62. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/person_enrichment.py +0 -0
  63. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/pinterest.py +0 -0
  64. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/playstore.py +0 -0
  65. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/polymarket.py +0 -0
  66. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/property_records.py +0 -0
  67. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/realtor.py +0 -0
  68. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/reddit.py +0 -0
  69. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/redfin.py +0 -0
  70. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/rednote.py +0 -0
  71. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/sec.py +0 -0
  72. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/semrush.py +0 -0
  73. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/seo.py +0 -0
  74. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/similarweb.py +0 -0
  75. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/snapchat.py +0 -0
  76. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/social.py +0 -0
  77. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/spotify.py +0 -0
  78. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/substack.py +0 -0
  79. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/technographics.py +0 -0
  80. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/threads.py +0 -0
  81. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/tiktok.py +0 -0
  82. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/tiktok_shop.py +0 -0
  83. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/tripadvisor.py +0 -0
  84. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/trustpilot.py +0 -0
  85. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/truthsocial.py +0 -0
  86. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/twitter.py +0 -0
  87. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/upwork.py +0 -0
  88. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/walmart.py +0 -0
  89. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/web.py +0 -0
  90. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/weibo.py +0 -0
  91. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/yahoo_finance.py +0 -0
  92. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/yelp.py +0 -0
  93. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/youtube.py +0 -0
  94. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/platforms/zhihu.py +0 -0
  95. {getanyapi-0.61.2 → getanyapi-0.63.0}/src/getanyapi/py.typed +0 -0
  96. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/conftest.py +0 -0
  97. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_client.py +0 -0
  98. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_durable_requests.py +0 -0
  99. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_envelope.py +0 -0
  100. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_errors.py +0 -0
  101. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_fixture_roundtrip.py +0 -0
  102. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_fixture_sweep.py +0 -0
  103. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_not_found_reason.py +0 -0
  104. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_pagination.py +0 -0
  105. {getanyapi-0.61.2 → getanyapi-0.63.0}/tests/test_transport.py +0 -0
  106. {getanyapi-0.61.2 → getanyapi-0.63.0}/uv.lock +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.5
2
2
  Name: getanyapi
3
- Version: 0.61.2
3
+ Version: 0.63.0
4
4
  Summary: Official typed Python SDK for AnyAPI: any API, one wallet, USD, no subscriptions.
5
5
  Project-URL: Homepage, https://getanyapi.com
6
6
  Project-URL: Documentation, https://getanyapi.com/docs
@@ -195,8 +195,9 @@ result = agent_signup(label="my-agent")
195
195
  client = AnyAPI(api_key=result.secret)
196
196
  ```
197
197
 
198
- The key ships with a small starter balance and a per-key spend cap; a human funds it by claiming
199
- it at `result.claim_url`.
198
+ The key ships with a small starter balance and a per-key spend cap; to go past the cap, a human
199
+ authorizes an AnyAPI wallet over OAuth, as described in
200
+ [agent self-signup](https://getanyapi.com/docs/agent-self-signup).
200
201
 
201
202
  ## Docs
202
203
 
@@ -166,8 +166,9 @@ result = agent_signup(label="my-agent")
166
166
  client = AnyAPI(api_key=result.secret)
167
167
  ```
168
168
 
169
- The key ships with a small starter balance and a per-key spend cap; a human funds it by claiming
170
- it at `result.claim_url`.
169
+ The key ships with a small starter balance and a per-key spend cap; to go past the cap, a human
170
+ authorizes an AnyAPI wallet over OAuth, as described in
171
+ [agent self-signup](https://getanyapi.com/docs/agent-self-signup).
171
172
 
172
173
  ## Docs
173
174
 
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
4
4
 
5
5
  [project]
6
6
  name = "getanyapi"
7
- version = "0.61.2"
7
+ version = "0.63.0"
8
8
  description = "Official typed Python SDK for AnyAPI: any API, one wallet, USD, no subscriptions."
9
9
  readme = "README.md"
10
10
  requires-python = ">=3.10"
@@ -55,7 +55,7 @@ from .types import (
55
55
  unwrap,
56
56
  )
57
57
 
58
- __version__ = "0.61.2"
58
+ __version__ = "0.63.0"
59
59
 
60
60
  __all__ = [
61
61
  # clients + top-level functions
@@ -746,7 +746,7 @@ class MapsNamespace:
746
746
  Fetch up to 100 Google Maps reviews for a place by place ID, sorted the way
747
747
  you need, in one normalized response.
748
748
 
749
- Price: $0.00605 per request plus $0.00005 per result (maximum $0.0105).
749
+ Price: $0.0035 per request.
750
750
 
751
751
  Example:
752
752
  res = client.maps.reviews(limit=3, placeId="ChIJN1t_tDeuEmsRUsoyG83frY4")
@@ -881,7 +881,7 @@ class AsyncMapsNamespace:
881
881
  Fetch up to 100 Google Maps reviews for a place by place ID, sorted the way
882
882
  you need, in one normalized response.
883
883
 
884
- Price: $0.00605 per request plus $0.00005 per result (maximum $0.0105).
884
+ Price: $0.0035 per request.
885
885
 
886
886
  Example:
887
887
  res = client.maps.reviews(limit=3, placeId="ChIJN1t_tDeuEmsRUsoyG83frY4")
@@ -15,6 +15,21 @@ if TYPE_CHECKING:
15
15
  from .._client import AnyAPI
16
16
 
17
17
 
18
+ class ZillowAgentInput(TypedDict, total=False):
19
+ """Input for Zillow Agent."""
20
+
21
+ allowFallbacks: NotRequired[bool]
22
+ """Optional, default true. When false, only the sources listed in `source` may serve; the request is refused with no charge if none of them can. When true, the listed sources are tried first and any other source may serve after them, at the normal price. Default: true."""
23
+ ignoreSources: NotRequired[list[str]]
24
+ """Optional. Source ids to skip for this request, taken from this endpoint's `lanes[].source.id`. The cheapest remaining source serves and the price is that of the dearest remaining source. An id that does not serve this endpoint, or that is also in `source`, is rejected as invalid input with no charge; skipping every source is rejected the same way."""
25
+ preferLatencyUnderMs: NotRequired[int]
26
+ """Optional; omit it and routing is unchanged, with the cheapest source serving. Prefer sources whose typical response time (median over the trailing 30 days, as published on this endpoint's lane health) is under this many milliseconds; among those, the cheapest serves. This can raise your price: when the cheapest source misses the target, a faster and dearer one serves, and you are quoted and charged its price. If no source is that fast the request is still served, by whichever source offers the best speed for its price - it is never refused for being slow. Sources we have not timed are tried last. This is a preference, not a guarantee: the median describes past requests and is not a ceiling on this one, and it excludes any wait this request itself asks for. On a paginated walk it applies to the first page only: later pages stay with the source that page chose, at the price it was quoted. Minimum: 1."""
27
+ source: NotRequired[list[str]]
28
+ """Optional. Source ids to prefer, in order, taken from this endpoint's `lanes[].source.id` in /catalog or /apis. Omit it and the cheapest source serves, with automatic failover. Listed sources are tried first in the order given, then the others, unless `allowFallbacks` is false. A single source with `allowFallbacks` false is served only by that source at its price, quoted and charged exactly, with no failover. The price is that of the dearest source that may serve. An id that does not serve this endpoint is rejected as invalid input with no charge; a listed source that is not serving right now is refused with no charge, so omit `source` to be served by another. On a paginated walk, later pages must include the source that served page one, or omit `source`."""
29
+ url: Required[str]
30
+ """Zillow agent profile URL (e.g. https://www.zillow.com/profile/gregorycarlsonATX/)."""
31
+
32
+
18
33
  class ZillowPropertyInput(TypedDict, total=False):
19
34
  """Input for Zillow Property."""
20
35
 
@@ -152,6 +167,67 @@ class ZillowSearchInput(TypedDict, total=False):
152
167
  """Optional. Source ids to prefer, in order, taken from this endpoint's `lanes[].source.id` in /catalog or /apis. Omit it and the cheapest source serves, with automatic failover. Listed sources are tried first in the order given, then the others, unless `allowFallbacks` is false. A single source with `allowFallbacks` false is served only by that source at its price, quoted and charged exactly, with no failover. The price is that of the dearest source that may serve. An id that does not serve this endpoint is rejected as invalid input with no charge; a listed source that is not serving right now is refused with no charge, so omit `source` to be served by another. On a paginated walk, later pages must include the source that served page one, or omit `source`."""
153
168
 
154
169
 
170
+ class ZillowAgentData(BaseModel):
171
+ model_config = ConfigDict(extra="allow", populate_by_name=True)
172
+
173
+ bio: str | None = Field(
174
+ default=None, description="Agent's self-written biography, as HTML."
175
+ )
176
+ company: str | None = Field(
177
+ default=None,
178
+ description="Brokerage or business name the agent works under. Populated whenever the provider has data for the entity. Present whenever the upstream returns this record.",
179
+ )
180
+ email: str | None = Field(
181
+ default=None,
182
+ description="Agent's email address as listed on the profile. Populated whenever the provider has data for the entity. Present whenever the upstream returns this record.",
183
+ )
184
+ for_sale_count: int | None = Field(
185
+ default=None,
186
+ alias="forSaleCount",
187
+ description="Number of active for-sale listings.",
188
+ )
189
+ image: str | None = Field(
190
+ default=None,
191
+ description="Profile photo URL. Populated whenever the provider has data for the entity. Present whenever the upstream returns this record.",
192
+ )
193
+ is_top_agent: bool | None = Field(
194
+ default=None,
195
+ alias="isTopAgent",
196
+ description="True when Zillow flags the agent as a top agent.",
197
+ )
198
+ name: str = Field(
199
+ description="Agent's full name. Populated whenever the provider has data for the entity."
200
+ )
201
+ phone: str | None = Field(
202
+ default=None,
203
+ description="Agent's phone number as listed on the profile (the cell number when one is listed). Populated whenever the provider has data for the entity. Present whenever the upstream returns this record.",
204
+ )
205
+ rating: float | None = Field(
206
+ default=None, description="Average review rating out of 5."
207
+ )
208
+ review_count: int | None = Field(
209
+ default=None,
210
+ alias="reviewCount",
211
+ description="Number of reviews on the profile.",
212
+ )
213
+ service_areas: list[str] | None = Field(
214
+ default=None,
215
+ alias="serviceAreas",
216
+ description='Cities and areas the agent lists as served, e.g. "Austin, TX".',
217
+ )
218
+ total_sales: int | None = Field(
219
+ default=None,
220
+ alias="totalSales",
221
+ description="Total sales on record for the agent (for a team lead, the team's total).",
222
+ )
223
+ url: str = Field(
224
+ description="Canonical Zillow profile URL. Populated whenever the provider has data for the entity."
225
+ )
226
+ username: str = Field(
227
+ description="Zillow screen name, the last segment of the profile URL. Populated whenever the provider has data for the entity."
228
+ )
229
+
230
+
155
231
  class ZillowPropertyData(BaseModel):
156
232
  items: list[ZillowPropertyItem] = Field(
157
233
  description="The matched property record (single element for a property lookup). Populated whenever the provider has data for the entity."
@@ -344,6 +420,27 @@ class ZillowNamespace:
344
420
  def __init__(self, client: "AnyAPI") -> None:
345
421
  self._client = client
346
422
 
423
+ def agent(
424
+ self,
425
+ *,
426
+ options: RequestOptions | None = None,
427
+ **input: Unpack[ZillowAgentInput],
428
+ ) -> RunResult[ZillowAgentData]:
429
+ """Zillow Agent
430
+
431
+ Fetch one Zillow real estate agent's profile by URL: name, phone, email,
432
+ brokerage, rating, review count, sales, and service areas.
433
+
434
+ Price: $0.0005 per request.
435
+
436
+ Example:
437
+ res = client.zillow.agent(url="https://www.zillow.com/profile/gregorycarlsonATX/")
438
+ """
439
+ raw = self._client._run_raw( # pyright: ignore[reportPrivateUsage]
440
+ "zillow.agent", dict(input), options
441
+ )
442
+ return RunResult[ZillowAgentData].model_validate(raw)
443
+
347
444
  def property(
348
445
  self,
349
446
  *,
@@ -396,6 +493,27 @@ class AsyncZillowNamespace:
396
493
  def __init__(self, client: "AsyncAnyAPI") -> None:
397
494
  self._client = client
398
495
 
496
+ async def agent(
497
+ self,
498
+ *,
499
+ options: RequestOptions | None = None,
500
+ **input: Unpack[ZillowAgentInput],
501
+ ) -> RunResult[ZillowAgentData]:
502
+ """Zillow Agent
503
+
504
+ Fetch one Zillow real estate agent's profile by URL: name, phone, email,
505
+ brokerage, rating, review count, sales, and service areas.
506
+
507
+ Price: $0.0005 per request.
508
+
509
+ Example:
510
+ res = client.zillow.agent(url="https://www.zillow.com/profile/gregorycarlsonATX/")
511
+ """
512
+ raw = await self._client._arun_raw( # pyright: ignore[reportPrivateUsage]
513
+ "zillow.agent", dict(input), options
514
+ )
515
+ return RunResult[ZillowAgentData].model_validate(raw)
516
+
399
517
  async def property(
400
518
  self,
401
519
  *,
@@ -10,7 +10,7 @@ unknown fields, exposed via ``.model_extra``.
10
10
 
11
11
  from __future__ import annotations
12
12
 
13
- from typing import Any, Generic, Literal, TypeVar, cast
13
+ from typing import Any, Generic, Literal, TypeVar, cast, get_args
14
14
 
15
15
  from pydantic import BaseModel, ConfigDict, Field, model_validator
16
16
  from typing_extensions import TypedDict
@@ -73,9 +73,10 @@ class OutputFound(BaseModel, Generic[T]):
73
73
  # words; ``tests/test_not_found_reason.py`` holds the two together once the live
74
74
  # OpenAPI carries the field. ``not_found``: the source states the target does not
75
75
  # exist, or returned nothing for it. ``suspended``: the platform has suspended the
76
- # account.
77
- NotFoundReason = Literal["not_found", "suspended"]
78
- NOT_FOUND_REASONS: tuple[str, ...] = ("not_found", "suspended")
76
+ # account. ``unavailable``: the platform did not show this to the source: it may not
77
+ # exist, or it may be visible only to signed-in users.
78
+ NotFoundReason = Literal["not_found", "suspended", "unavailable"]
79
+ NOT_FOUND_REASONS: tuple[str, ...] = get_args(NotFoundReason)
79
80
 
80
81
 
81
82
  class OutputNotFound(BaseModel):
@@ -283,8 +284,6 @@ class AgentSignupResult(BaseModel):
283
284
 
284
285
  secret: str
285
286
  cap_usd: float = Field(alias="capUsd")
286
- claim_token: str = Field(alias="claimToken")
287
- claim_url: str = Field(alias="claimUrl")
288
287
 
289
288
 
290
289
  # Convenience aliases used by the transport for untyped generic runs.
@@ -464,23 +464,30 @@ def test_describe_404_raises_not_found() -> None:
464
464
  client.describe("nope.gone")
465
465
 
466
466
 
467
- def test_agent_signup_maps_result(monkeypatch: pytest.MonkeyPatch) -> None:
467
+ SIGNUP_BODY: dict[str, object] = {"secret": "sk_live_x", "capUsd": 0.15, "keyId": "key_1"}
468
+ # The gateway still sends these retired claim-flow fields until it drops them.
469
+ RETIRED_SIGNUP_FIELDS: dict[str, object] = {
470
+ "verificationStatus": "pending",
471
+ "claimToken": "",
472
+ "claimUrl": "https://getanyapi.com/dashboard",
473
+ }
474
+
475
+
476
+ @pytest.mark.parametrize(
477
+ "body",
478
+ [SIGNUP_BODY, {**SIGNUP_BODY, **RETIRED_SIGNUP_FIELDS}],
479
+ ids=["without-retired-fields", "with-retired-fields"],
480
+ )
481
+ def test_agent_signup_maps_result(
482
+ monkeypatch: pytest.MonkeyPatch, body: dict[str, object]
483
+ ) -> None:
468
484
  captured: dict[str, object] = {}
469
485
 
470
486
  def handler(request: httpx.Request) -> httpx.Response:
471
487
  captured["path"] = request.url.path
472
488
  captured["auth"] = request.headers.get("authorization")
473
489
  captured["body"] = json.loads(request.content)
474
- return json_response(
475
- 200,
476
- {
477
- "secret": "sk_live_x",
478
- "capUsd": 0.15,
479
- "claimToken": "tok",
480
- "claimUrl": "https://getanyapi.com/dashboard",
481
- "keyId": "key_1",
482
- },
483
- )
490
+ return json_response(200, body)
484
491
 
485
492
  transport = httpx.MockTransport(handler)
486
493
  import getanyapi._client as client_mod
@@ -498,8 +505,6 @@ def test_agent_signup_maps_result(monkeypatch: pytest.MonkeyPatch) -> None:
498
505
  assert captured["body"] == {"sponsorEmail": "me@x.com", "label": "bot"}
499
506
  assert result.secret == "sk_live_x"
500
507
  assert result.cap_usd == 0.15
501
- assert result.claim_token == "tok"
502
- assert result.claim_url == "https://getanyapi.com/dashboard"
503
508
 
504
509
 
505
510
  async def test_async_account() -> None:
File without changes
File without changes
File without changes