mirror of
https://gitlab.com/MoonTestUse1/AdministrationItDepartmens.git
synced 2025-08-14 00:25:46 +02:00
Все подряд
This commit is contained in:
119
.venv2/Lib/site-packages/telethon/tl/custom/qrlogin.py
Normal file
119
.venv2/Lib/site-packages/telethon/tl/custom/qrlogin.py
Normal file
@@ -0,0 +1,119 @@
|
||||
import asyncio
|
||||
import base64
|
||||
import datetime
|
||||
|
||||
from .. import types, functions
|
||||
from ... import events
|
||||
|
||||
|
||||
class QRLogin:
|
||||
"""
|
||||
QR login information.
|
||||
|
||||
Most of the time, you will present the `url` as a QR code to the user,
|
||||
and while it's being shown, call `wait`.
|
||||
"""
|
||||
def __init__(self, client, ignored_ids):
|
||||
self._client = client
|
||||
self._request = functions.auth.ExportLoginTokenRequest(
|
||||
self._client.api_id, self._client.api_hash, ignored_ids)
|
||||
self._resp = None
|
||||
|
||||
async def recreate(self):
|
||||
"""
|
||||
Generates a new token and URL for a new QR code, useful if the code
|
||||
has expired before it was imported.
|
||||
"""
|
||||
self._resp = await self._client(self._request)
|
||||
|
||||
@property
|
||||
def token(self) -> bytes:
|
||||
"""
|
||||
The binary data representing the token.
|
||||
|
||||
It can be used by a previously-authorized client in a call to
|
||||
:tl:`auth.importLoginToken` to log the client that originally
|
||||
requested the QR login.
|
||||
"""
|
||||
return self._resp.token
|
||||
|
||||
@property
|
||||
def url(self) -> str:
|
||||
"""
|
||||
The ``tg://login`` URI with the token. When opened by a Telegram
|
||||
application where the user is logged in, it will import the login
|
||||
token.
|
||||
|
||||
If you want to display a QR code to the user, this is the URL that
|
||||
should be launched when the QR code is scanned (the URL that should
|
||||
be contained in the QR code image you generate).
|
||||
|
||||
Whether you generate the QR code image or not is up to you, and the
|
||||
library can't do this for you due to the vast ways of generating and
|
||||
displaying the QR code that exist.
|
||||
|
||||
The URL simply consists of `token` base64-encoded.
|
||||
"""
|
||||
return 'tg://login?token={}'.format(base64.urlsafe_b64encode(self._resp.token).decode('utf-8').rstrip('='))
|
||||
|
||||
@property
|
||||
def expires(self) -> datetime.datetime:
|
||||
"""
|
||||
The `datetime` at which the QR code will expire.
|
||||
|
||||
If you want to try again, you will need to call `recreate`.
|
||||
"""
|
||||
return self._resp.expires
|
||||
|
||||
async def wait(self, timeout: float = None):
|
||||
"""
|
||||
Waits for the token to be imported by a previously-authorized client,
|
||||
either by scanning the QR, launching the URL directly, or calling the
|
||||
import method.
|
||||
|
||||
This method **must** be called before the QR code is scanned, and
|
||||
must be executing while the QR code is being scanned. Otherwise, the
|
||||
login will not complete.
|
||||
|
||||
Will raise `asyncio.TimeoutError` if the login doesn't complete on
|
||||
time.
|
||||
|
||||
Arguments
|
||||
timeout (float):
|
||||
The timeout, in seconds, to wait before giving up. By default
|
||||
the library will wait until the token expires, which is often
|
||||
what you want.
|
||||
|
||||
Returns
|
||||
On success, an instance of :tl:`User`. On failure it will raise.
|
||||
"""
|
||||
if timeout is None:
|
||||
timeout = (self._resp.expires - datetime.datetime.now(tz=datetime.timezone.utc)).total_seconds()
|
||||
|
||||
event = asyncio.Event()
|
||||
|
||||
async def handler(_update):
|
||||
event.set()
|
||||
|
||||
self._client.add_event_handler(handler, events.Raw(types.UpdateLoginToken))
|
||||
|
||||
try:
|
||||
# Will raise timeout error if it doesn't complete quick enough,
|
||||
# which we want to let propagate
|
||||
await asyncio.wait_for(event.wait(), timeout=timeout)
|
||||
finally:
|
||||
self._client.remove_event_handler(handler)
|
||||
|
||||
# We got here without it raising timeout error, so we can proceed
|
||||
resp = await self._client(self._request)
|
||||
if isinstance(resp, types.auth.LoginTokenMigrateTo):
|
||||
await self._client._switch_dc(resp.dc_id)
|
||||
resp = await self._client(functions.auth.ImportLoginTokenRequest(resp.token))
|
||||
# resp should now be auth.loginTokenSuccess
|
||||
|
||||
if isinstance(resp, types.auth.LoginTokenSuccess):
|
||||
user = resp.authorization.user
|
||||
await self._client._on_login(user)
|
||||
return user
|
||||
|
||||
raise TypeError('Login token response was unexpected: {}'.format(resp))
|
||||
Reference in New Issue
Block a user