Retry up to five times before giving up on a request

This commit is contained in:
Lonami Exo 2017-09-11 10:52:36 +02:00
parent 880f5636be
commit 48dead76ac
2 changed files with 17 additions and 9 deletions

View File

@ -282,7 +282,7 @@ class TelegramBareClient:
# region Invoking Telegram requests # region Invoking Telegram requests
def invoke(self, request, updates=None, call_receive=True): def invoke(self, request, call_receive=True, retries=5):
"""Invokes (sends) a MTProtoRequest and returns (receives) its result. """Invokes (sends) a MTProtoRequest and returns (receives) its result.
If 'updates' is not None, all read update object will be put If 'updates' is not None, all read update object will be put
@ -298,6 +298,9 @@ class TelegramBareClient:
if not self._sender: if not self._sender:
raise ValueError('You must be connected to invoke requests!') raise ValueError('You must be connected to invoke requests!')
if retries <= 0:
raise ValueError('Number of retries reached 0.')
try: try:
# Ensure that we start with no previous errors (i.e. resending) # Ensure that we start with no previous errors (i.e. resending)
request.confirm_received.clear() request.confirm_received.clear()
@ -314,20 +317,24 @@ class TelegramBareClient:
while not request.confirm_received.is_set(): while not request.confirm_received.is_set():
self._sender.receive(update_state=self.updates) self._sender.receive(update_state=self.updates)
if request.rpc_error:
raise request.rpc_error
return request.result
except ConnectionResetError: except ConnectionResetError:
self._logger.debug('Server disconnected us. Reconnecting and ' self._logger.debug('Server disconnected us. Reconnecting and '
'resending request...') 'resending request...')
self.reconnect() self.reconnect()
return self.invoke(request)
except FloodWaitError: except FloodWaitError:
self.disconnect() self.disconnect()
raise raise
if request.rpc_error:
raise request.rpc_error
if request.result is None:
return self.invoke(
request, call_receive=call_receive, retries=(retries - 1)
)
else:
return request.result
# Let people use client(SomeRequest()) instead client.invoke(...) # Let people use client(SomeRequest()) instead client.invoke(...)
__call__ = invoke __call__ = invoke

View File

@ -218,8 +218,9 @@ class TelegramClient(TelegramBareClient):
# region Telegram requests functions # region Telegram requests functions
def invoke(self, request, *args): def invoke(self, request, *args, **kwargs):
"""Invokes (sends) a MTProtoRequest and returns (receives) its result. """Invokes (sends) a MTProtoRequest and returns (receives) its result.
An optional 'retries' parameter can be set.
*args will be ignored. *args will be ignored.
""" """
@ -233,9 +234,9 @@ class TelegramClient(TelegramBareClient):
# will be the one which should be reading (but is invoking the # will be the one which should be reading (but is invoking the
# request) thus not being available to read it "in the background" # request) thus not being available to read it "in the background"
# and it's needed to call receive. # and it's needed to call receive.
# TODO Retry if 'result' is None?
return super().invoke( return super().invoke(
request, call_receive=self._recv_thread is None request, call_receive=self._recv_thread is None,
retries=kwargs.get('retries', 5)
) )
except (PhoneMigrateError, NetworkMigrateError, UserMigrateError) as e: except (PhoneMigrateError, NetworkMigrateError, UserMigrateError) as e: