[commands] Use eval instead of get_type_hints to resolve typehints
The previous usage of `typing.get_type_hints` caused issues as it would incorrectly decide to convert annotations into their equivalent `typing` form -- which is not what we want to happen here. Due to some use-cases about how setting `Command.callback` work and the amount of moving parts that have changed due to this patch, it is probably better to refactor the way it is set so users can have this use-case handled transparently for them.
This commit is contained in:
parent
ee57e89488
commit
fdc71695dc
@ -174,21 +174,7 @@ class Command:
|
|||||||
self.description = inspect.cleandoc(kwargs.get('description', ''))
|
self.description = inspect.cleandoc(kwargs.get('description', ''))
|
||||||
self.hidden = kwargs.get('hidden', False)
|
self.hidden = kwargs.get('hidden', False)
|
||||||
|
|
||||||
signature = inspect.signature(callback)
|
|
||||||
annotations = typing.get_type_hints(callback)
|
|
||||||
|
|
||||||
self.params = signature.parameters.copy()
|
|
||||||
|
|
||||||
# PEP-563 allows postponing evaluation of annotations with a __future__
|
|
||||||
# import. When postponed, Parameter.annotation will be a string and must
|
|
||||||
# be replaced with the real class from typing.get_type_hints() for the
|
|
||||||
# converters to work later on
|
|
||||||
for key, value in self.params.items():
|
|
||||||
if isinstance(value.annotation, str) and key in annotations:
|
|
||||||
self.params[key] = value.replace(annotation=annotations[key])
|
|
||||||
|
|
||||||
self.checks = kwargs.get('checks', [])
|
self.checks = kwargs.get('checks', [])
|
||||||
self.module = callback.__module__
|
|
||||||
self.ignore_extra = kwargs.get('ignore_extra', True)
|
self.ignore_extra = kwargs.get('ignore_extra', True)
|
||||||
self.instance = None
|
self.instance = None
|
||||||
self.parent = None
|
self.parent = None
|
||||||
@ -196,6 +182,25 @@ class Command:
|
|||||||
self._before_invoke = None
|
self._before_invoke = None
|
||||||
self._after_invoke = None
|
self._after_invoke = None
|
||||||
|
|
||||||
|
@property
|
||||||
|
def callback(self):
|
||||||
|
return self._callback
|
||||||
|
|
||||||
|
@callback.setter
|
||||||
|
def callback(self, function):
|
||||||
|
self._callback = function
|
||||||
|
self.module = function.__module__
|
||||||
|
|
||||||
|
signature = inspect.signature(function)
|
||||||
|
self.params = signature.parameters.copy()
|
||||||
|
|
||||||
|
# PEP-563 allows postponing evaluation of annotations with a __future__
|
||||||
|
# import. When postponed, Parameter.annotation will be a string and must
|
||||||
|
# be replaced with the real value for the converters to work later on
|
||||||
|
for key, value in self.params.items():
|
||||||
|
if isinstance(value.annotation, str):
|
||||||
|
self.params[key] = value.replace(annotation=eval(value.annotation, function.__globals__))
|
||||||
|
|
||||||
async def dispatch_error(self, ctx, error):
|
async def dispatch_error(self, ctx, error):
|
||||||
ctx.command_failed = True
|
ctx.command_failed = True
|
||||||
cog = self.instance
|
cog = self.instance
|
||||||
|
Loading…
x
Reference in New Issue
Block a user