2
0
mirror of https://github.com/pyrogram/pyrogram synced 2025-08-24 19:07:57 +00:00

Rework user.status, add last_online_date and next_offline_date

This commit is contained in:
Dan 2019-07-11 01:35:02 +02:00
parent f9ea45f987
commit 2f07e7abc4
4 changed files with 97 additions and 43 deletions

View File

@ -77,9 +77,7 @@ class Dispatcher:
lambda upd, usr, cht: (pyrogram.CallbackQuery._parse(self.client, upd, usr), CallbackQueryHandler), lambda upd, usr, cht: (pyrogram.CallbackQuery._parse(self.client, upd, usr), CallbackQueryHandler),
(types.UpdateUserStatus,): (types.UpdateUserStatus,):
lambda upd, usr, cht: ( lambda upd, usr, cht: (pyrogram.User._parse_user_status(self.client, upd), UserStatusHandler),
pyrogram.UserStatus._parse(self.client, upd.status, upd.user_id), UserStatusHandler
),
(types.UpdateBotInlineQuery,): (types.UpdateBotInlineQuery,):
lambda upd, usr, cht: (pyrogram.InlineQuery._parse(self.client, upd, usr), InlineQueryHandler), lambda upd, usr, cht: (pyrogram.InlineQuery._parse(self.client, upd, usr), InlineQueryHandler),

View File

@ -21,26 +21,24 @@ from .handler import Handler
class UserStatusHandler(Handler): class UserStatusHandler(Handler):
"""The UserStatus handler class. Used to handle user status updates (user going online or offline). """The UserStatus handler class. Used to handle user status updates (user going online or offline).
It is intended to be used with :meth:`~Client.add_handler` It is intended to be used with :meth:`~Client.add_handler`.
For a nicer way to register this handler, have a look at the For a nicer way to register this handler, have a look at the :meth:`~Client.on_user_status` decorator.
:meth:`~Client.on_user_status` decorator.
Parameters: Parameters:
callback (``callable``): callback (``callable``):
Pass a function that will be called when a new UserStatus update arrives. It takes *(client, user_status)* Pass a function that will be called when a new user status update arrives. It takes *(client, user)*
as positional arguments (look at the section below for a detailed description). as positional arguments (look at the section below for a detailed description).
filters (:obj:`Filters`): filters (:obj:`Filters`):
Pass one or more filters to allow only a subset of messages to be passed Pass one or more filters to allow only a subset of users to be passed in your callback function.
in your callback function.
Other parameters: Other parameters:
client (:obj:`Client`): client (:obj:`Client`):
The Client itself, useful when you want to call other API methods inside the user status handler. The Client itself, useful when you want to call other API methods inside the user status handler.
user_status (:obj:`UserStatus`): user (:obj:`User`):
The received UserStatus update. The user containing the updated status.
""" """
def __init__(self, callback: callable, filters=None): def __init__(self, callback: callable, filters=None):

View File

@ -23,8 +23,7 @@ from .chat_photo import ChatPhoto
from .chat_preview import ChatPreview from .chat_preview import ChatPreview
from .dialog import Dialog from .dialog import Dialog
from .user import User from .user import User
from .user_status import UserStatus
__all__ = [ __all__ = [
"Chat", "ChatMember", "ChatPermissions", "ChatPhoto", "ChatPreview", "Dialog", "User", "UserStatus" "Chat", "ChatMember", "ChatPermissions", "ChatPhoto", "ChatPreview", "Dialog", "User"
] ]

View File

@ -21,54 +21,68 @@ import html
import pyrogram import pyrogram
from pyrogram.api import types from pyrogram.api import types
from .chat_photo import ChatPhoto from .chat_photo import ChatPhoto
from .user_status import UserStatus
from ..object import Object from ..object import Object
from ..update import Update
class User(Object): class User(Object, Update):
"""A Telegram user or bot. """A Telegram user or bot.
Parameters: Parameters:
id (``int``): id (``int``):
Unique identifier for this user or bot. Unique identifier for this user or bot.
is_self(``bool``): is_self(``bool``, *optional*):
True, if this user is you yourself. True, if this user is you yourself.
is_contact(``bool``): is_contact(``bool``, *optional*):
True, if this user is in your contacts. True, if this user is in your contacts.
is_mutual_contact(``bool``): is_mutual_contact(``bool``, *optional*):
True, if you both have each other's contact. True, if you both have each other's contact.
is_deleted(``bool``): is_deleted(``bool``, *optional*):
True, if this user is deleted. True, if this user is deleted.
is_bot (``bool``): is_bot (``bool``, *optional*):
True, if this user is a bot. True, if this user is a bot.
is_verified (``bool``): is_verified (``bool``, *optional*):
True, if this user has been verified by Telegram. True, if this user has been verified by Telegram.
is_restricted (``bool``): is_restricted (``bool``, *optional*):
True, if this user has been restricted. Bots only. True, if this user has been restricted. Bots only.
See *restriction_reason* for details. See *restriction_reason* for details.
is_scam (``bool``): is_scam (``bool``, *optional*):
True, if this user has been flagged for scam. True, if this user has been flagged for scam.
is_support (``bool``): is_support (``bool``, *optional*):
True, if this user is part of the Telegram support team. True, if this user is part of the Telegram support team.
first_name (``str``): first_name (``str``, *optional*):
User's or bot's first name. User's or bot's first name.
status (:obj:`UserStatus <pyrogram.UserStatus>`, *optional*):
User's Last Seen status. Empty for bots.
last_name (``str``, *optional*): last_name (``str``, *optional*):
User's or bot's last name. User's or bot's last name.
status (``str``, *optional*):
User's Last Seen & Online status.
Can be one of the following:
"*online*", user is online right now.
"*offline*", user is currently offline.
"*recently*", user with hidden last seen time who was online between 1 second and 2-3 days ago.
"*within_week*", user with hidden last seen time who was online between 2-3 and seven days ago.
"*within_month*", user with hidden last seen time who was online between 6-7 days and a month ago.
"*long_time_ago*", blocked user or user with hidden last seen time who was online more than a month ago.
*None*, for bots.
last_online_date (``int``, *optional*):
Last online date of a user. Only available in case status is "*offline*".
next_offline_date (``int``, *optional*):
Date when a user will automatically go offline. Only available in case status is "*online*".
username (``str``, *optional*): username (``str``, *optional*):
User's or bot's username. User's or bot's username.
@ -77,7 +91,7 @@ class User(Object):
dc_id (``int``, *optional*): dc_id (``int``, *optional*):
User's or bot's assigned DC (data center). Available only in case the user has set a public profile photo. User's or bot's assigned DC (data center). Available only in case the user has set a public profile photo.
Note that this information is approximate: it is based on where Telegram stores a user profile pictures and Note that this information is approximate; it is based on where Telegram stores a user profile pictures and
does not by any means tell you the user location (i.e. a user might travel far away, but will still connect does not by any means tell you the user location (i.e. a user might travel far away, but will still connect
to its assigned DC). More info at `FAQs </faq#what-are-the-ip-addresses-of-telegram-data-centers>`_. to its assigned DC). More info at `FAQs </faq#what-are-the-ip-addresses-of-telegram-data-centers>`_.
@ -94,8 +108,8 @@ class User(Object):
__slots__ = [ __slots__ = [
"id", "is_self", "is_contact", "is_mutual_contact", "is_deleted", "is_bot", "is_verified", "is_restricted", "id", "is_self", "is_contact", "is_mutual_contact", "is_deleted", "is_bot", "is_verified", "is_restricted",
"is_scam", "is_support", "first_name", "last_name", "status", "username", "language_code", "dc_id", "is_scam", "is_support", "first_name", "last_name", "status", "last_online_date", "next_offline_date",
"phone_number", "photo", "restriction_reason" "username", "language_code", "dc_id", "phone_number", "photo", "restriction_reason"
] ]
def __init__( def __init__(
@ -103,18 +117,20 @@ class User(Object):
*, *,
client: "pyrogram.BaseClient" = None, client: "pyrogram.BaseClient" = None,
id: int, id: int,
is_self: bool, is_self: bool = None,
is_contact: bool, is_contact: bool = None,
is_mutual_contact: bool, is_mutual_contact: bool = None,
is_deleted: bool, is_deleted: bool = None,
is_bot: bool, is_bot: bool = None,
is_verified: bool, is_verified: bool = None,
is_restricted: bool, is_restricted: bool = None,
is_scam: bool, is_scam: bool = None,
is_support: bool, is_support: bool = None,
first_name: str, first_name: str = None,
last_name: str = None, last_name: str = None,
status: UserStatus = None, status: str = None,
last_online_date: int = None,
next_offline_date: int = None,
username: str = None, username: str = None,
language_code: str = None, language_code: str = None,
dc_id: int = None, dc_id: int = None,
@ -137,6 +153,8 @@ class User(Object):
self.first_name = first_name self.first_name = first_name
self.last_name = last_name self.last_name = last_name
self.status = status self.status = status
self.last_online_date = last_online_date
self.next_offline_date = next_offline_date
self.username = username self.username = username
self.language_code = language_code self.language_code = language_code
self.dc_id = dc_id self.dc_id = dc_id
@ -168,7 +186,7 @@ class User(Object):
is_support=user.support, is_support=user.support,
first_name=user.first_name, first_name=user.first_name,
last_name=user.last_name, last_name=user.last_name,
status=UserStatus._parse(client, user.status, user.id, user.bot), **User._parse_status(user.status, user.bot),
username=user.username, username=user.username,
language_code=user.lang_code, language_code=user.lang_code,
dc_id=getattr(user.photo, "dc_id", None), dc_id=getattr(user.photo, "dc_id", None),
@ -178,6 +196,47 @@ class User(Object):
client=client client=client
) )
@staticmethod
def _parse_status(user_status: types.UpdateUserStatus, is_bot: bool = False):
if isinstance(user_status, types.UserStatusOnline):
status, date = "online", user_status.expires
elif isinstance(user_status, types.UserStatusOffline):
status, date = "offline", user_status.was_online
elif isinstance(user_status, types.UserStatusRecently):
status, date = "recently", None
elif isinstance(user_status, types.UserStatusLastWeek):
status, date = "within_week", None
elif isinstance(user_status, types.UserStatusLastMonth):
status, date = "within_month", None
else:
status, date = "long_time_ago", None
last_online_date = None
next_offline_date = None
if is_bot:
status = None
if status == "online":
next_offline_date = date
if status == "offline":
last_online_date = date
return {
"status": status,
"last_online_date": last_online_date,
"next_offline_date": next_offline_date
}
@staticmethod
def _parse_user_status(client, user_status: types.UpdateUserStatus):
return User(
id=user_status.user_id,
**User._parse_status(user_status.status),
client=client
)
def archive(self): def archive(self):
"""Bound method *archive* of :obj:`User`. """Bound method *archive* of :obj:`User`.