diff --git a/discord/abc.py b/discord/abc.py index 9b66b33fd..726fe5567 100644 --- a/discord/abc.py +++ b/discord/abc.py @@ -802,7 +802,9 @@ class GuildChannel: await http.delete_channel_permissions(self.id, target.id, reason=reason) elif isinstance(overwrite, PermissionOverwrite): (allow, deny) = overwrite.pair() - await http.edit_channel_permissions(self.id, target.id, str(allow.value), str(deny.value), perm_type, reason=reason) + await http.edit_channel_permissions( + self.id, target.id, str(allow.value), str(deny.value), perm_type, reason=reason + ) else: raise InvalidArgument('Invalid overwrite type provided.') diff --git a/discord/components.py b/discord/components.py index 0c6ec9004..4e40ccd11 100644 --- a/discord/components.py +++ b/discord/components.py @@ -126,7 +126,7 @@ class ActionRow(Component): return { 'type': int(self.type), 'components': [child.to_dict() for child in self.children], - } # type: ignore + } # type: ignore - Type checker does not understand these are the same class Button(Component): @@ -198,7 +198,7 @@ class Button(Component): if self.emoji: payload['emoji'] = self.emoji.to_dict() - return payload # type: ignore + return payload # type: ignore - Type checker does not understand these are the same class SelectMenu(Component): @@ -364,7 +364,7 @@ class SelectOption: } if self.emoji: - payload['emoji'] = self.emoji.to_dict() # type: ignore + payload['emoji'] = self.emoji.to_dict() # type: ignore - This Dict[str, Any] is compatible with PartialEmoji if self.description: payload['description'] = self.description @@ -462,10 +462,13 @@ def _component_factory(data: ComponentPayload) -> Component: if component_type == 1: return ActionRow(data) elif component_type == 2: + # The type checker does not properly do narrowing here. return Button(data) # type: ignore elif component_type == 3: + # The type checker does not properly do narrowing here. return SelectMenu(data) # type: ignore elif component_type == 4: + # The type checker does not properly do narrowing here. return TextInput(data) # type: ignore else: as_enum = try_enum(ComponentType, component_type) diff --git a/discord/embeds.py b/discord/embeds.py index 5ad28830d..59914f0ea 100644 --- a/discord/embeds.py +++ b/discord/embeds.py @@ -311,7 +311,7 @@ class Embed: return getattr(self, '_colour', EmptyEmbed) @colour.setter - def colour(self, value: Union[int, Colour, _EmptyEmbed]): # type: ignore + def colour(self, value: Union[int, Colour, _EmptyEmbed]): if isinstance(value, (Colour, _EmptyEmbed)): self._colour = value elif isinstance(value, int): @@ -344,6 +344,7 @@ class Embed: If the attribute has no value then :attr:`Empty` is returned. """ + # Lying to the type checker for better developer UX. return EmbedProxy(getattr(self, '_footer', {})) # type: ignore def set_footer(self: E, *, text: MaybeEmpty[Any] = EmptyEmbed, icon_url: MaybeEmpty[Any] = EmptyEmbed) -> E: @@ -397,6 +398,7 @@ class Embed: If the attribute has no value then :attr:`Empty` is returned. """ + # Lying to the type checker for better developer UX. return EmbedProxy(getattr(self, '_image', {})) # type: ignore def set_image(self: E, *, url: MaybeEmpty[Any]) -> E: @@ -439,6 +441,7 @@ class Embed: If the attribute has no value then :attr:`Empty` is returned. """ + # Lying to the type checker for better developer UX. return EmbedProxy(getattr(self, '_thumbnail', {})) # type: ignore def set_thumbnail(self: E, *, url: MaybeEmpty[Any]) -> E: @@ -480,6 +483,7 @@ class Embed: If the attribute has no value then :attr:`Empty` is returned. """ + # Lying to the type checker for better developer UX. return EmbedProxy(getattr(self, '_video', {})) # type: ignore @property @@ -490,6 +494,7 @@ class Embed: If the attribute has no value then :attr:`Empty` is returned. """ + # Lying to the type checker for better developer UX. return EmbedProxy(getattr(self, '_provider', {})) # type: ignore @property @@ -500,6 +505,7 @@ class Embed: If the attribute has no value then :attr:`Empty` is returned. """ + # Lying to the type checker for better developer UX. return EmbedProxy(getattr(self, '_author', {})) # type: ignore def set_author(self: E, *, name: Any, url: MaybeEmpty[Any] = EmptyEmbed, icon_url: MaybeEmpty[Any] = EmptyEmbed) -> E: @@ -553,6 +559,7 @@ class Embed: If the attribute has no value then :attr:`Empty` is returned. """ + # Lying to the type checker for better developer UX. return [EmbedProxy(d) for d in getattr(self, '_fields', [])] # type: ignore def add_field(self: E, *, name: Any, value: Any, inline: bool = True) -> E: @@ -726,4 +733,4 @@ class Embed: if self.title: result['title'] = self.title - return result # type: ignore + return result # type: ignore - This payload is equivalent to the EmbedData type diff --git a/discord/enums.py b/discord/enums.py index b39832bc3..5b5b46d96 100644 --- a/discord/enums.py +++ b/discord/enums.py @@ -24,7 +24,7 @@ DEALINGS IN THE SOFTWARE. import types from collections import namedtuple -from typing import Any, ClassVar, Dict, List, Optional, TYPE_CHECKING, Type, TypeVar +from typing import Any, ClassVar, Dict, List, Optional, TYPE_CHECKING, Tuple, Type, TypeVar __all__ = ( 'Enum', @@ -59,15 +59,17 @@ __all__ = ( ) -def _create_value_cls(name, comparable): +def _create_value_cls(name: str, comparable: bool): + # All the type ignores here are due to the type checker being unable to recognise + # Runtime type creation without exploding. cls = namedtuple('_EnumValue_' + name, 'name value') - cls.__repr__ = lambda self: f'<{name}.{self.name}: {self.value!r}>' - cls.__str__ = lambda self: f'{name}.{self.name}' + cls.__repr__ = lambda self: f'<{name}.{self.name}: {self.value!r}>' # type: ignore + cls.__str__ = lambda self: f'{name}.{self.name}' # type: ignore if comparable: - cls.__le__ = lambda self, other: isinstance(other, self.__class__) and self.value <= other.value - cls.__ge__ = lambda self, other: isinstance(other, self.__class__) and self.value >= other.value - cls.__lt__ = lambda self, other: isinstance(other, self.__class__) and self.value < other.value - cls.__gt__ = lambda self, other: isinstance(other, self.__class__) and self.value > other.value + cls.__le__ = lambda self, other: isinstance(other, self.__class__) and self.value <= other.value # type: ignore + cls.__ge__ = lambda self, other: isinstance(other, self.__class__) and self.value >= other.value # type: ignore + cls.__lt__ = lambda self, other: isinstance(other, self.__class__) and self.value < other.value # type: ignore + cls.__gt__ = lambda self, other: isinstance(other, self.__class__) and self.value > other.value # type: ignore return cls @@ -82,7 +84,7 @@ class EnumMeta(type): _enum_member_map_: ClassVar[Dict[str, Any]] _enum_value_map_: ClassVar[Dict[Any, Any]] - def __new__(cls, name, bases, attrs, *, comparable: bool = False): + def __new__(cls: Type[type], name: str, bases: Tuple[type, ...], attrs: Dict[str, Any], *, comparable: bool = False): value_mapping = {} member_mapping = {} member_names = [] @@ -117,7 +119,7 @@ class EnumMeta(type): attrs['_enum_member_names_'] = member_names attrs['_enum_value_cls_'] = value_cls actual_cls = super().__new__(cls, name, bases, attrs) - value_cls._actual_enum_cls_ = actual_cls # type: ignore + value_cls._actual_enum_cls_ = actual_cls # type: ignore - Runtime attribute isn't understood return actual_cls def __iter__(cls): @@ -607,22 +609,22 @@ class NSFWLevel(Enum, comparable=True): age_restricted = 3 -T = TypeVar('T') +E = TypeVar('E', bound='Enum') -def create_unknown_value(cls: Type[T], val: Any) -> T: - value_cls = cls._enum_value_cls_ # type: ignore +def create_unknown_value(cls: Type[E], val: Any) -> E: + value_cls = cls._enum_value_cls_ # type: ignore - This is narrowed below name = f'unknown_{val}' return value_cls(name=name, value=val) -def try_enum(cls: Type[T], val: Any) -> T: +def try_enum(cls: Type[E], val: Any) -> E: """A function that tries to turn the value into enum ``cls``. If it fails it returns a proxy invalid value instead. """ try: - return cls._enum_value_map_[val] # type: ignore + return cls._enum_value_map_[val] # type: ignore - All errors are caught below except (KeyError, TypeError, AttributeError): return create_unknown_value(cls, val) diff --git a/discord/errors.py b/discord/errors.py index bc2398d55..0aea1d112 100644 --- a/discord/errors.py +++ b/discord/errors.py @@ -125,7 +125,7 @@ class HTTPException(DiscordException): def __init__(self, response: _ResponseType, message: Optional[Union[str, Dict[str, Any]]]): self.response: _ResponseType = response - self.status: int = response.status # type: ignore + self.status: int = response.status # type: ignore - This attribute is filled by the library even if using requests self.code: int self.text: str if isinstance(message, dict): diff --git a/discord/ui/text_input.py b/discord/ui/text_input.py index bde7a093b..a23d9b82a 100644 --- a/discord/ui/text_input.py +++ b/discord/ui/text_input.py @@ -47,6 +47,7 @@ __all__ = ( V = TypeVar('V', bound='View', covariant=True) TI = TypeVar('TI', bound='TextInput') + class TextInput(Item[V]): """Represents a UI text input.