99
1010from aiohttp import web
1111
12- from twitchio import CustomReward , PartialUser , parse_timestamp as _parse_datetime
12+ from twitchio import PartialUser , parse_timestamp as _parse_datetime
1313
1414if TYPE_CHECKING :
1515 from .server import EventSubClient
@@ -382,6 +382,109 @@ def __init__(self, client: EventSubClient, data: dict):
382382 self .broadcaster = _transform_user (client , data , "broadcaster_user" )
383383
384384
385+ class CustomReward :
386+ """
387+ A Custom Reward
388+
389+ Attributes
390+ -----------
391+ broadcaster: :class:`twitchio.PartialUser`
392+ The channel that has this reward
393+ id: :class:`str`
394+ The ID of the reward
395+ title: :class:`str`
396+ The title of the reward
397+ cost: :class:`int`
398+ The cost of the reward in Channel Points
399+ prompt: :class:`str`
400+ The prompt of the reward
401+ enabled: Optional[:class:`bool`]
402+ Whether or not the reward is enabled. Will be `None` for Redemption events.
403+ paused: Optional[:class:`bool`]
404+ Whether or not the reward is paused. Will be `None` for Redemption events.
405+ in_stock: Optional[:class:`bool`]
406+ Whether or not the reward is in stock. Will be `None` for Redemption events.
407+ cooldown_until: Optional[:class:`datetime.datetime`]
408+ How long until the reward is off cooldown and can be redeemed again. Will be `None` for Redemption events.
409+ input_required: Optional[:class:`bool`]
410+ Whether or not the reward requires an input. Will be `None` for Redemption events.
411+ redemptions_skip_queue: Optional[:class:`bool`]
412+ Whether or not redemptions for this reward skips the queue. Will be `None` for Redemption events.
413+ redemptions_current_stream: Optional[:class:`int`]
414+ How many redemptions of this reward have been redeemed for this stream. Will be `None` for Redemption events.
415+ max_per_stream: Tuple[:class:`bool`, :class:`int`]
416+ Whether or not a per-stream redemption limit is in place, and if so, the maximum number of redemptions allowed
417+ per stream. Will be `None` for Redemption events.
418+ max_per_user_per_stream: Tuple[:class:`bool`, :class:`int`]
419+ Whether or not a per-user-per-stream redemption limit is in place, and if so, the maximum number of redemptions
420+ allowed per user per stream. Will be `None` for Redemption events.
421+ cooldown: Tuple[:class:`bool`, :class:`int`]
422+ Whether or not a global cooldown is in place, and if so, the number of seconds until the reward can be redeemed
423+ again. Will be `None` for Redemption events.
424+ background_color: Optional[:class:`str`]
425+ Hexadecimal color code for the background of the reward.
426+ image: Optional[:class:`str`]
427+ Image URL for the reward.
428+ """
429+
430+ __slots__ = (
431+ "broadcaster" ,
432+ "id" ,
433+ "title" ,
434+ "cost" ,
435+ "prompt" ,
436+ "enabled" ,
437+ "paused" ,
438+ "in_stock" ,
439+ "cooldown_until" ,
440+ "input_required" ,
441+ "redemptions_skip_queue" ,
442+ "redemptions_current_stream" ,
443+ "max_per_stream" ,
444+ "max_per_user_stream" ,
445+ "cooldown" ,
446+ "background_color" ,
447+ "image" ,
448+ )
449+
450+ def __init__ (self , data , broadcaster ):
451+ self .broadcaster : PartialUser = broadcaster
452+
453+ self .id : str = data ["id" ]
454+
455+ self .title : str = data ["title" ]
456+ self .cost : int = data ["cost" ]
457+ self .prompt : str = data ["prompt" ]
458+
459+ self .enabled : bool = data .get ("is_enabled" , None )
460+ self .paused : bool = data .get ("is_paused" , None )
461+ self .in_stock : bool = data .get ("is_in_stock" , None )
462+
463+ self .cooldown_until : datetime .datetime = (
464+ _parse_datetime (data ["cooldown_expires_at" ]) if data .get ("cooldown_expires_at" , None ) else None
465+ )
466+
467+ self .input_required : bool = data .get ("is_user_input_required" , None )
468+ self .redemptions_skip_queue : bool = data .get ("should_redemptions_skip_request_queue" , None )
469+ self .redemptions_current_stream : bool = data .get ("redemptions_redeemed_current_stream" , None )
470+
471+ self .max_per_stream : tuple [bool , int ] = (
472+ data .get ("max_per_stream" , {}).get ("is_enabled" ),
473+ data .get ("max_per_stream" , {}).get ("value" ),
474+ )
475+ self .max_per_user_stream : tuple [bool , int ] = (
476+ data .get ("max_per_user_per_stream" , {}).get ("is_enabled" ),
477+ data .get ("max_per_user_per_stream" , {}).get ("value" ),
478+ )
479+ self .cooldown : tuple [bool , int ] = (
480+ data .get ("global_cooldown" , {}).get ("is_enabled" ),
481+ data .get ("global_cooldown" , {}).get ("seconds" ),
482+ )
483+
484+ self .background_color : str = data .get ("background_color" , None )
485+ self .image : str = data .get ("image" , data .get ("default_image" , {})).get ("url_1x" , None )
486+
487+
385488class CustomRewardAddUpdateRemoveData (EventData ):
386489 """
387490 A Custom Reward Add/Update/Remove event
@@ -392,7 +495,7 @@ class CustomRewardAddUpdateRemoveData(EventData):
392495 The ID of the custom reward
393496 broadcaster: :class:`twitchio.PartialUser`
394497 The channel the custom reward was modified in
395- reward: :class:`twitchio. CustomReward`
498+ reward: :class:`CustomReward`
396499 The reward object
397500 """
398501
@@ -401,7 +504,7 @@ class CustomRewardAddUpdateRemoveData(EventData):
401504 def __init__ (self , client : EventSubClient , data : dict ):
402505 self .id : str = data ["id" ]
403506 self .broadcaster = _transform_user (client , data , "broadcaster_user" )
404- self .reward = CustomReward (client . client . _http , data , self .broadcaster )
507+ self .reward = CustomReward (data , self .broadcaster )
405508
406509
407510class CustomRewardRedemptionAddUpdateData (EventData ):
@@ -422,7 +525,7 @@ class CustomRewardRedemptionAddUpdateData(EventData):
422525 One of "unknown", "unfulfilled", "fulfilled", or "cancelled"
423526 redeemed_at: :class:`datetime.datetime`
424527 When the reward was redeemed at
425- reward: :class:`twitchio. CustomReward`
528+ reward: :class:`CustomReward`
426529 The reward object
427530 """
428531
@@ -435,7 +538,7 @@ def __init__(self, client: EventSubClient, data: dict):
435538 self .input : str = data ["user_input" ]
436539 self .status : Literal ["unknown" , "unfulfilled" , "fulfilled" , "cancelled" ] = data ["status" ]
437540 self .redeemed_at = _parse_datetime (data ["redeemed_at" ])
438- self .reward = CustomReward (client . client . _http , data ["reward" ], self .broadcaster )
541+ self .reward = CustomReward (data ["reward" ], self .broadcaster )
439542
440543
441544class HypeTrainContributor :
0 commit comments