Ejemplo n.º 1
0
    def get_dialogs_count(self, pinned_only: bool = False) -> int:
        """Get the total count of your dialogs.

        pinned_only (``bool``, *optional*):
            Pass True if you want to count only pinned dialogs.
            Defaults to False.

        Returns:
            ``int``: On success, the dialogs count is returned.

        Raises:
            RPCError: In case of a Telegram RPC error.
        """

        if pinned_only:
            return len(
                self.send(
                    functions.messages.GetPinnedDialogs(folder_id=0)).dialogs)
        else:
            r = self.send(
                functions.messages.GetDialogs(
                    offset_date=0,
                    offset_id=0,
                    offset_peer=types.InputPeerEmpty(),
                    limit=1,
                    hash=0))

            if isinstance(r, types.messages.Dialogs):
                return len(r.dialogs)
            else:
                return r.count
Ejemplo n.º 2
0
    async def get_dialogs_count(self, pinned_only: bool = False) -> int:
        """Get the total count of your dialogs.

        pinned_only (``bool``, *optional*):
            Pass True if you want to count only pinned dialogs.
            Defaults to False.

        Returns:
            ``int``: On success, the dialogs count is returned.

        Example:
            .. code-block:: python

                count = app.get_dialogs_count()
                print(count)
        """

        if pinned_only:
            return len((await self.send(functions.messages.GetPinnedDialogs(folder_id=0))).dialogs)
        else:
            r = await self.send(
                functions.messages.GetDialogs(
                    offset_date=0,
                    offset_id=0,
                    offset_peer=types.InputPeerEmpty(),
                    limit=1,
                    hash=0
                )
            )

            if isinstance(r, types.messages.Dialogs):
                return len(r.dialogs)
            else:
                return r.count
Ejemplo n.º 3
0
    def get_dialogs(
        self,
        offset_date: int = 0,
        limit: int = 100,
        pinned_only: bool = False
    ) -> "pyrogram.Dialogs":
        """Get a chunk of the user's dialogs.

        You can get up to 100 dialogs at once.
        For a more convenient way of getting a user's dialogs see :meth:`~Client.iter_dialogs`.

        Parameters:
            offset_date (``int``):
                The offset date in Unix time taken from the top message of a :obj:`Dialog`.
                Defaults to 0. Valid for non-pinned dialogs only.

            limit (``str``, *optional*):
                Limits the number of dialogs to be retrieved.
                Defaults to 100. Valid for non-pinned dialogs only.

            pinned_only (``bool``, *optional*):
                Pass True if you want to get only pinned dialogs.
                Defaults to False.

        Returns:
            :obj:`Dialogs`: On success, an object containing a list of dialogs is returned.

        Raises:
            RPCError: In case of a Telegram RPC error.
        """

        while True:
            try:
                if pinned_only:
                    r = self.send(functions.messages.GetPinnedDialogs(folder_id=0))
                else:
                    r = self.send(
                        functions.messages.GetDialogs(
                            offset_date=offset_date,
                            offset_id=0,
                            offset_peer=types.InputPeerEmpty(),
                            limit=limit,
                            hash=0,
                            exclude_pinned=True
                        )
                    )
            except FloodWait as e:
                log.warning("Sleeping {}s".format(e.x))
                time.sleep(e.x)
            else:
                break

        return pyrogram.Dialogs._parse(self, r)
Ejemplo n.º 4
0
 def get_dialogs_chunk(self, offset_date):
     while True:
         try:
             r = self.send(
                 functions.messages.GetDialogs(offset_date, 0,
                                               types.InputPeerEmpty(),
                                               self.DIALOGS_AT_ONCE, True))
         except FloodWait as e:
             log.warning("get_dialogs flood: waiting {} seconds".format(
                 e.x))
             time.sleep(e.x)
         else:
             log.info("Total peers: {}".format(len(self.peers_by_id)))
             return r
Ejemplo n.º 5
0
 def get_initial_dialogs_chunk(self, offset_date: int = 0):
     while True:
         try:
             r = self.send(
                 functions.messages.GetDialogs(
                     offset_date=offset_date,
                     offset_id=0,
                     offset_peer=types.InputPeerEmpty(),
                     limit=self.DIALOGS_AT_ONCE,
                     hash=0,
                     exclude_pinned=True
                 )
             )
         except FloodWait as e:
             log.warning("get_dialogs flood: waiting {} seconds".format(e.x))
             time.sleep(e.x)
         else:
             log.info("Total peers: {}".format(len(self.peers_by_id)))
             return r
Ejemplo n.º 6
0
    def get_dialogs(self,
                    offset_date: int = 0,
                    limit: int = 100,
                    pinned_only: bool = False) -> "pyrogram.Dialogs":
        """Use this method to get the user's dialogs

        You can get up to 100 dialogs at once.

        Args:
            offset_date (``int``):
                The offset date in Unix time taken from the top message of a :obj:`Dialog`.
                Defaults to 0. Valid for non-pinned dialogs only.

            limit (``str``, *optional*):
                Limits the number of dialogs to be retrieved.
                Defaults to 100. Valid for non-pinned dialogs only.

            pinned_only (``bool``, *optional*):
                Pass True if you want to get only pinned dialogs.
                Defaults to False.

        Returns:
            On success, a :obj:`Dialogs` object is returned.

        Raises:
            :class:`Error <pyrogram.Error>` in case of a Telegram RPC error.
        """

        if pinned_only:
            r = self.send(functions.messages.GetPinnedDialogs())
        else:
            r = self.send(
                functions.messages.GetDialogs(
                    offset_date=offset_date,
                    offset_id=0,
                    offset_peer=types.InputPeerEmpty(),
                    limit=limit,
                    hash=0,
                    exclude_pinned=True))

        return pyrogram.Dialogs._parse(self, r)
Ejemplo n.º 7
0
    async def get_dialogs(
            self,
            offset_date: int = 0,
            limit: int = 100,
            pinned_only: bool = False) -> List["pyrogram.Dialog"]:
        """Get a chunk of the user's dialogs.

        You can get up to 100 dialogs at once.
        For a more convenient way of getting a user's dialogs see :meth:`~Client.iter_dialogs`.

        Parameters:
            offset_date (``int``):
                The offset date in Unix time taken from the top message of a :obj:`Dialog`.
                Defaults to 0. Valid for non-pinned dialogs only.

            limit (``str``, *optional*):
                Limits the number of dialogs to be retrieved.
                Defaults to 100. Valid for non-pinned dialogs only.

            pinned_only (``bool``, *optional*):
                Pass True if you want to get only pinned dialogs.
                Defaults to False.

        Returns:
            List of :obj:`Dialog`: On success, a list of dialogs is returned.

        Example:
            .. code-block:: python

                # Get first 100 dialogs
                app.get_dialogs()

                # Get pinned dialogs
                app.get_dialogs(pinned_only=True)
        """

        while True:
            try:
                if pinned_only:
                    r = await self.send(
                        functions.messages.GetPinnedDialogs(folder_id=0))
                else:
                    r = await self.send(
                        functions.messages.GetDialogs(
                            offset_date=offset_date,
                            offset_id=0,
                            offset_peer=types.InputPeerEmpty(),
                            limit=limit,
                            hash=0,
                            exclude_pinned=True))
            except FloodWait as e:
                log.warning("Sleeping for {}s".format(e.x))
                await asyncio.sleep(e.x)
            else:
                break

        users = {i.id: i for i in r.users}
        chats = {i.id: i for i in r.chats}

        messages = {}

        for message in r.messages:
            to_id = message.to_id

            if isinstance(to_id, types.PeerUser):
                if message.out:
                    chat_id = to_id.user_id
                else:
                    chat_id = message.from_id
            else:
                chat_id = utils.get_peer_id(to_id)

            messages[chat_id] = await pyrogram.Message._parse(
                self, message, users, chats)

        parsed_dialogs = []

        for dialog in r.dialogs:
            if not isinstance(dialog, types.Dialog):
                continue

            parsed_dialogs.append(
                pyrogram.Dialog._parse(self, dialog, messages, users, chats))

        return pyrogram.List(parsed_dialogs)
Ejemplo n.º 8
0
    async def search_global(
        self,
        query: str,
        limit: int = 0,
    ) -> Optional[Generator["pyrogram.Message", None, None]]:
        """Search messages globally from all of your chats.

        .. note::

            Due to server-side limitations, you can only get up to around ~10,000 messages and each message
            retrieved will not have any *reply_to_message* field.

        Parameters:
            query (``str``):
                Text query string.

            limit (``int``, *optional*):
                Limits the number of messages to be retrieved.
                By default, no limit is applied and all messages are returned.

        Returns:
            ``Generator``: A generator yielding :obj:`Message` objects.

        Example:
            .. code-block:: python

                # Search for "pyrogram". Get the first 420 results
                for message in app.search_global("pyrogram", limit=420):
                    print(message.text)
        """
        current = 0
        # There seems to be an hard limit of 10k, beyond which Telegram starts spitting one message at a time.
        total = abs(limit) or (1 << 31)
        limit = min(100, total)

        offset_date = 0
        offset_peer = types.InputPeerEmpty()
        offset_id = 0

        while True:
            messages = await utils.parse_messages(
                self,
                await self.send(
                    functions.messages.SearchGlobal(q=query,
                                                    offset_rate=offset_date,
                                                    offset_peer=offset_peer,
                                                    offset_id=offset_id,
                                                    limit=limit)),
                replies=0)

            if not messages:
                return

            last = messages[-1]

            offset_date = last.date
            offset_peer = await self.resolve_peer(last.chat.id)
            offset_id = last.message_id

            for message in messages:
                await yield_(message)

                current += 1

                if current >= total:
                    return
Ejemplo n.º 9
0
    def get_dialogs(self,
                    offset_dialogs=None,
                    limit: int = 100,
                    pinned_only: bool = False):
        """Use this method to get the user's dialogs

        You can get up to 100 dialogs at once.

        Args:
            limit (``str``, *optional*):
                Limits the number of dialogs to be retrieved.
                Defaults to 100

            pinned_only (``bool``, *optional*):
                Pass True if you want to get only pinned dialogs.
                Defaults to False.

            offset_dialogs (:obj:`Dialogs`):
                Pass the previous dialogs object to retrieve the next dialogs chunk starting from the last dialog.
                Defaults to None (start from the beginning).

        Returns:
            On success, a :obj:`Dialogs` object is returned.

        Raises:
            :class:`Error <pyrogram.Error>` in case of a Telegram RPC error.
        """

        if pinned_only:
            r = self.send(functions.messages.GetPinnedDialogs())
        else:
            offset_date = 0

            if offset_dialogs:
                for dialog in reversed(offset_dialogs.dialogs):
                    top_message = dialog.top_message

                    if top_message:
                        message_date = top_message.date

                        if message_date:
                            offset_date = message_date
                            break

            r = self.send(
                functions.messages.GetDialogs(
                    offset_date=offset_date,
                    offset_id=0,
                    offset_peer=types.InputPeerEmpty(),
                    limit=limit,
                    hash=0,
                    exclude_pinned=True))

        users = {i.id: i for i in r.users}
        chats = {i.id: i for i in r.chats}
        messages = {}

        for message in r.messages:
            to_id = message.to_id

            if isinstance(to_id, types.PeerUser):
                if message.out:
                    chat_id = to_id.user_id
                else:
                    chat_id = message.from_id
            elif isinstance(to_id, types.PeerChat):
                chat_id = -to_id.chat_id
            else:
                chat_id = int("-100" + str(to_id.channel_id))

            messages[chat_id] = utils.parse_messages(self, message, users,
                                                     chats)

        dialogs = []

        for dialog in r.dialogs:
            chat_id = dialog.peer

            if isinstance(chat_id, types.PeerUser):
                chat_id = chat_id.user_id
            elif isinstance(chat_id, types.PeerChat):
                chat_id = -chat_id.chat_id
            else:
                chat_id = int("-100" + str(chat_id.channel_id))

            dialogs.append(
                pyrogram.Dialog(
                    chat=utils.parse_dialog_chat(dialog.peer, users, chats),
                    top_message=messages.get(chat_id),
                    unread_messages_count=dialog.unread_count,
                    unread_mentions_count=dialog.unread_mentions_count,
                    unread_mark=dialog.unread_mark,
                    is_pinned=dialog.pinned))

        return pyrogram.Dialogs(total_count=getattr(r, "count",
                                                    len(r.dialogs)),
                                dialogs=dialogs)