Make distribution_type optional in DropBenefitSchema and add test for missing field
This commit is contained in:
parent
5504f59952
commit
835a0e0e2a
2 changed files with 129 additions and 1 deletions
|
|
@ -88,7 +88,7 @@ class DropBenefitSchema(BaseModel):
|
||||||
created_at: str | None = Field(default=None, alias="createdAt")
|
created_at: str | None = Field(default=None, alias="createdAt")
|
||||||
entitlement_limit: int = Field(default=1, alias="entitlementLimit")
|
entitlement_limit: int = Field(default=1, alias="entitlementLimit")
|
||||||
is_ios_available: bool = Field(default=False, alias="isIosAvailable")
|
is_ios_available: bool = Field(default=False, alias="isIosAvailable")
|
||||||
distribution_type: str = Field(alias="distributionType")
|
distribution_type: str | None = Field(default=None, alias="distributionType") # Optional in some API responses
|
||||||
type_name: Literal["Benefit", "DropBenefit"] = Field(alias="__typename")
|
type_name: Literal["Benefit", "DropBenefit"] = Field(alias="__typename")
|
||||||
# API response fields that should be ignored
|
# API response fields that should be ignored
|
||||||
game: dict | None = None
|
game: dict | None = None
|
||||||
|
|
|
||||||
|
|
@ -245,3 +245,131 @@ def test_graphql_response_with_errors() -> None:
|
||||||
assert response.data.current_user.twitch_id == "17658559"
|
assert response.data.current_user.twitch_id == "17658559"
|
||||||
assert response.data.current_user.drop_campaigns is not None
|
assert response.data.current_user.drop_campaigns is not None
|
||||||
assert len(response.data.current_user.drop_campaigns) == 1
|
assert len(response.data.current_user.drop_campaigns) == 1
|
||||||
|
|
||||||
|
|
||||||
|
def test_drop_campaign_details_missing_distribution_type() -> None:
|
||||||
|
"""Test that DropCampaignDetails operation validates when distributionType is missing.
|
||||||
|
|
||||||
|
Some API responses (e.g., from DropCampaignDetails operation) don't include
|
||||||
|
the distributionType field in the benefit object. The schema should handle this
|
||||||
|
gracefully by making the field optional.
|
||||||
|
|
||||||
|
This is based on a real-world validation error from file 7720168310842708008.json.
|
||||||
|
"""
|
||||||
|
payload = {
|
||||||
|
"data": {
|
||||||
|
"user": {
|
||||||
|
"id": "58162970",
|
||||||
|
"dropCampaign": {
|
||||||
|
"id": "1cf86f25-540f-11ef-90d0-0a58a9feac02",
|
||||||
|
"self": {
|
||||||
|
"isAccountConnected": False,
|
||||||
|
"__typename": "DropCampaignSelfEdge",
|
||||||
|
},
|
||||||
|
"allow": {
|
||||||
|
"channels": [
|
||||||
|
{
|
||||||
|
"id": "182565961",
|
||||||
|
"displayName": "WorldofWarships",
|
||||||
|
"name": "worldofwarships",
|
||||||
|
"__typename": "Channel",
|
||||||
|
},
|
||||||
|
],
|
||||||
|
"isEnabled": True,
|
||||||
|
"__typename": "DropCampaignACL",
|
||||||
|
},
|
||||||
|
"accountLinkURL": "https://wargaming.net/personal/",
|
||||||
|
"description": "New Drops!",
|
||||||
|
"detailsURL": "https://worldofwarships.eu/news/general-news/stream-rewards-137/",
|
||||||
|
"endAt": "2024-08-21T21:59:59.996Z",
|
||||||
|
"eventBasedDrops": [],
|
||||||
|
"game": {
|
||||||
|
"id": "32502",
|
||||||
|
"slug": "world-of-warships",
|
||||||
|
"displayName": "World of Warships",
|
||||||
|
"__typename": "Game",
|
||||||
|
},
|
||||||
|
"imageURL": "https://static-cdn.jtvnw.net/twitch-quests-assets/CAMPAIGN/51ec1931-6792-4b9f-850a-e6b9c454eefc.png",
|
||||||
|
"name": "Official Channel Weekly Drop",
|
||||||
|
"owner": {
|
||||||
|
"id": "6948a129-2c6d-4d88-9444-6b96918a19f8",
|
||||||
|
"name": "Wargaming",
|
||||||
|
"__typename": "Organization",
|
||||||
|
},
|
||||||
|
"startAt": "2024-08-14T22:00:00Z",
|
||||||
|
"status": "ACTIVE",
|
||||||
|
"timeBasedDrops": [
|
||||||
|
{
|
||||||
|
"id": "79a0a4db-5a4d-11ef-91b7-0a58a9feac02",
|
||||||
|
"requiredSubs": 0,
|
||||||
|
"benefitEdges": [
|
||||||
|
{
|
||||||
|
"benefit": {
|
||||||
|
"id": "6948a129-2c6d-4d88-9444-6b96918a19f8_CUSTOM_ID_WOWS_TwitchDrops_1307_250ct", # noqa: E501
|
||||||
|
"createdAt": "2024-08-06T16:03:15.89Z",
|
||||||
|
"entitlementLimit": 1,
|
||||||
|
"game": {
|
||||||
|
"id": "32502",
|
||||||
|
"name": "World of Warships",
|
||||||
|
"__typename": "Game",
|
||||||
|
},
|
||||||
|
"imageAssetURL": "https://static-cdn.jtvnw.net/twitch-quests-assets/REWARD/a049fb1a-ab63-40e5-9a43-bd6b94e52f36.png",
|
||||||
|
"isIosAvailable": False,
|
||||||
|
"name": "13.7 Update: 250 CT",
|
||||||
|
"ownerOrganization": {
|
||||||
|
"id": "6948a129-2c6d-4d88-9444-6b96918a19f8",
|
||||||
|
"name": "Wargaming",
|
||||||
|
"__typename": "Organization",
|
||||||
|
},
|
||||||
|
"__typename": "DropBenefit",
|
||||||
|
},
|
||||||
|
"entitlementLimit": 1,
|
||||||
|
"__typename": "DropBenefitEdge",
|
||||||
|
},
|
||||||
|
],
|
||||||
|
"endAt": "2024-08-21T21:59:59.996Z",
|
||||||
|
"name": "Week 2: 250 Community Tokens",
|
||||||
|
"preconditionDrops": None,
|
||||||
|
"requiredMinutesWatched": 60,
|
||||||
|
"startAt": "2024-08-14T22:00:00Z",
|
||||||
|
"__typename": "TimeBasedDrop",
|
||||||
|
},
|
||||||
|
],
|
||||||
|
"__typename": "DropCampaign",
|
||||||
|
},
|
||||||
|
"__typename": "User",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
"extensions": {
|
||||||
|
"durationMilliseconds": 75,
|
||||||
|
"operationName": "DropCampaignDetails",
|
||||||
|
"requestID": "01J5RDFXF7VMMDWVBZKNZ52ED6",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
# This should not raise ValidationError despite missing distributionType
|
||||||
|
response = GraphQLResponse.model_validate(payload)
|
||||||
|
|
||||||
|
# Verify the structure was parsed correctly
|
||||||
|
assert response.data.current_user is not None
|
||||||
|
assert response.data.current_user.twitch_id == "58162970"
|
||||||
|
|
||||||
|
# Verify drop_campaigns was normalized from dropCampaign (singular)
|
||||||
|
assert response.data.current_user.drop_campaigns is not None
|
||||||
|
assert len(response.data.current_user.drop_campaigns) == 1
|
||||||
|
|
||||||
|
campaign = response.data.current_user.drop_campaigns[0]
|
||||||
|
assert campaign.name == "Official Channel Weekly Drop"
|
||||||
|
assert campaign.game.display_name == "World of Warships"
|
||||||
|
assert len(campaign.time_based_drops) == 1
|
||||||
|
|
||||||
|
# Verify time-based drops
|
||||||
|
first_drop = campaign.time_based_drops[0]
|
||||||
|
assert first_drop.name == "Week 2: 250 Community Tokens"
|
||||||
|
assert first_drop.required_minutes_watched == 60
|
||||||
|
|
||||||
|
# Verify benefits - distributionType should be None since it was missing
|
||||||
|
assert len(first_drop.benefit_edges) == 1
|
||||||
|
benefit = first_drop.benefit_edges[0].benefit
|
||||||
|
assert benefit.name == "13.7 Update: 250 CT"
|
||||||
|
assert benefit.distribution_type is None # This field was missing in the API response
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue