コード例 #1
0
    async def quote_stats(self, ctx: commands.Context):
        """!kazhelp
        description: Get quote statistics.
        """
        em = discord.Embed(title="Quote statistics")
        em.add_field(name="Total quotes", value=str(c.get_total_quotes()))
        em.add_field(name="Quoted users",
                     value=str(c.get_total_quoted_users()))

        most_quoted = c.get_top_quoted()
        most_quoted_strs = [
            '{.name} ({} quotes)'.format(u, total) for u, total in most_quoted
        ]
        em.add_field(name="Most quoted",
                     value='{}'.format(format_list(most_quoted_strs)))

        most_saved = c.get_top_saved()
        most_saved_strs = [
            '{.name} ({} quotes saved)'.format(u, total)
            for u, total in most_saved
        ]
        em.add_field(name="Top quoters",
                     value='{}'.format(format_list(most_saved_strs)))

        await self.send_message(ctx.message.channel, embed=em)
コード例 #2
0
    def format_list(reminders: List[ReminderData]) -> str:
        """ Format the input list for sending to a user. """
        items = []
        for reminder in reminders:
            build_str = []

            if reminder.channel_id:
                build_str.append(
                    "In {channel} at {remind_time} UTC (in {delta})")
            else:
                build_str.append("At {remind_time} UTC (in {delta})")

            if reminder.renew_data:
                renew_data = reminder.renew_data
                build_str.append(" and every {interval}")
                if renew_data.limit_time:
                    build_str.append(" until {limit_time} up to")
                build_str.append(" {limit} times")

            build_str.append(": {message}")

            items.append(''.join(build_str).format(
                delta=format_timedelta(reminder.remind_time -
                                       datetime.utcnow()),
                **reminder.str_dict(),
                **(reminder.renew_data.str_dict()
                   if reminder.renew_data else {})))
        return format_list(items) if items else 'None'
コード例 #3
0
ファイル: spotlight.py プロジェクト: r-Worldbuilding/kaztron
    async def queue_list(self, ctx):
        """
        [MOD ONLY] Lists the current queue of upcoming spotlights.
        """
        logger.debug("queue list: {}".format(message_log_str(ctx.message)))
        self._load_applications()
        logger.info("Listing queue for {0.author!s} in {0.channel!s}".format(ctx.message))

        app_strings = self._get_queue_list()
        if app_strings:
            app_list_string = format_list(app_strings)
        else:
            app_list_string = 'Empty'
        await self.send_embed_list(title=self.QUEUE_HEADING, contents=app_list_string)
コード例 #4
0
    async def finduser(self, ctx, search_term: str, page: int = 1):
        """

        [MOD ONLY] User search.

        This command searches the name and aliases fields.

        Arguments:
        * <search_term>: Required. A substring to search for in the user database's name and aliases
          fields.

        Example:

        .notes finduser Indium
            If there is a user called "IndiumPhosphide", they would be matched.
        """
        search_term_s = search_term[:Limits.NAME]
        logger.info("notes finduser: {}".format(message_log_str(ctx.message)))

        # Get results
        results = c.search_users(search_term_s)

        # Prepare for display
        len_results = len(results)
        total_pages = int(math.ceil(len_results / self.USEARCH_PAGE_SIZE))
        page = max(1, min(total_pages, page))

        results_lines = []
        start_index = (page - 1) * self.USEARCH_PAGE_SIZE
        end_index = start_index + self.USEARCH_PAGE_SIZE

        for user in results[start_index:end_index]:
            matched_alias = self._find_match_field(user, search_term_s)

            # Format this user for the list display
            if not matched_alias:
                results_lines.append("{} - Canonical name: {}".format(
                    self.format_display_user(user), user.name))
            else:
                results_lines.append("{} - Alias: {}".format(
                    self.format_display_user(user), matched_alias.name))

        # Output - should always be sub-2000 characters (given length limits + page size)
        heading = self.USEARCH_HEADING_F.format(page=page,
                                                pages=total_pages,
                                                total=len_results,
                                                query=search_term_s)
        await self.bot.say("{}\n\n{}".format(heading,
                                             format_list(results_lines)))
コード例 #5
0
    async def subwatch(self, ctx: commands.Context):
        """!kazhelp

        brief: Show Subwatch configuration.
        description: Show the current subwatch configuration.
        """
        channel_strings = []
        for channel, ch_info in self.cog_state.channels.items():
            channel_strings.append("{}: {}".format(
                channel.mention,
                ', '.join('/r/' + name for name in ch_info.subreddits)))
        await self.send_message(
            ctx.message.channel, ctx.message.author.mention + '\n' +
            (format_list(channel_strings)
             if channel_strings else 'No subwatch configured'))
コード例 #6
0
    async def filter_list(self, ctx, filter_type: str = None):
        """!kazhelp
        description: |
            Lists the current filters.

            If `filter_type` is not given, lists all filters; otherwise, lists the specified filter.
        parameters:
            - name: filter_type
              optional: True
              default: both
              description: "Filter list: `del` or `warn` (shorthand: `d` or `w`)."
        examples:
            - command: .filter list
              description: Shows both auto-warn and auto-delete lists.
            - command: .filter list warn
              description: Shows warn filter list.
            - command: .filter list del
              description: Shows auto-delete filter list.
            - command: .filter l w
              description: "Shorthand version of `.filter list warn`."
        """
        if filter_type is None:  # not passed - list both
            await ctx.invoke(self.filter_list, 'del')
            await ctx.invoke(self.filter_list, 'warn')
        else:
            validated_type = await self.validate_filter_type(filter_type)
            if validated_type is None:
                # error messages and logging already managed
                return

            logger.info("filter_list: listing '{}' list for {}".format(
                validated_type, ctx.message.author))
            filter_list = self.cog_state.get(validated_type)
            if filter_list:
                list_str = format_list(filter_list)
            else:
                list_str = 'Empty'

            heading_str = self.list_headings[validated_type]
            say_strings = split_code_chunks_on(
                list_str, MSG_MAX_LEN - len(heading_str) - 2)
            await self.bot.say("{}\n{}".format(heading_str, say_strings[0]))
            for say_str in say_strings[1:]:
                await self.bot.say(say_str)
コード例 #7
0
    async def filter_list(self, ctx, filter_type: str = None):
        """
        [MOD ONLY] Lists the current filters.

        If `filter_type` is not given, lists all filters; otherwise, lists the specified filter.

        Examples:

        .filter list - Shows both auto-warn and auto-delete lists.
        .filter list warn - Shows warn filter list.
        .filter list del - Shows auto-delete filter list.

        You can use single-letter mnemonics for convenience:

        .filter l w - Shows warn filter list.
        """
        logger.info("filter_list: {}".format(message_log_str(ctx.message)))
        if filter_type is None:  # not passed - list both
            await ctx.invoke(self.filter_list, 'del')
            await ctx.invoke(self.filter_list, 'warn')
        else:
            validated_type = await self.validate_filter_type(filter_type)
            if validated_type is None:
                # error messages and logging already managed
                return

            logger.info("filter_list: listing '{}' list for {}".format(
                validated_type, ctx.message.author))
            filter_list = self.filter_cfg.get("filter", validated_type)
            if filter_list:
                list_str = format_list(filter_list)
            else:
                list_str = 'Empty'

            heading_str = self.list_headings[validated_type]
            say_strings = split_code_chunks_on(
                list_str, MSG_MAX_LEN - len(heading_str) - 2)
            await self.bot.say("{}\n{}".format(heading_str, say_strings[0]))
            for say_str in say_strings[1:]:
                await self.bot.say(say_str)
コード例 #8
0
    async def list(self, ctx: commands.Context):
        """ Lists all future reminders you've requested. """
        logger.info("reminder list: {}".format(message_log_str(ctx.message)))

        items = []
        filtered = filter(lambda r: r.user_id == ctx.message.author.id, self.reminders)
        sorted_reminders = sorted(filtered, key=lambda r: r.remind_time)
        for reminder in sorted_reminders:
            items.append("At {} UTC (in {}): {}".format(
                format_datetime(reminder.remind_time),
                format_timedelta(reminder.remind_time - datetime.utcnow()),
                reminder.message
            ))
        if items:
            reminder_list = format_list(items)
        else:
            reminder_list = 'None'
        await self.bot.send_message(ctx.message.author, "**Your reminders**\n" + reminder_list)
        try:
            await self.bot.delete_message(ctx.message)
        except discord.Forbidden:
            pass  # no permission or in a PM; oh well, this is not critical
コード例 #9
0
ファイル: spotlight.py プロジェクト: r-Worldbuilding/kaztron
    async def queue_showcase(self, ctx, *, month: NaturalDateConverter=None):
        """
        [MOD ONLY] Lists a month's queue in the showcase format.

        Arguments:
        * month: Optional. Specify the month to list applications for. Default: next month.

        Examples:
            .spotlight q s 2018-03
            .spotlight q s March 2018
        """
        logger.debug("queue showcase: {}".format(message_log_str(ctx.message)))
        self._load_applications()
        logger.info("Listing showcase queue for {0.author!s} in {0.channel!s}".format(ctx.message))
        month = month  # type: datetime

        # figure out month start/end times
        if not month:
            month = get_month_offset(datetime.utcnow(), 1)
        else:
            month = truncate(month, 'month')
        month_end = get_month_offset(month, 1)
        month_ts, month_end_ts = utctimestamp(month), utctimestamp(month_end)

        app_strings = self._get_queue_list(showcase=True)

        # filter by month
        filt_app_strings = []
        for queue_item, app_string in zip(self.queue_data, app_strings):
            if month_ts <= queue_item['start'] < month_end_ts:
                filt_app_strings.append(app_string)

        if filt_app_strings:
            app_list_string = format_list(filt_app_strings)
        else:
            app_list_string = 'Empty'
        await self.bot.say('{}\n```{}```'.format(self.QUEUE_HEADING, app_list_string))
コード例 #10
0
ファイル: spotlight.py プロジェクト: r-Worldbuilding/kaztron
    async def list(self, ctx):
        """
        [MOD ONLY] List all the spotlight applications in summary form.
        """
        logger.debug("list: {}".format(message_log_str(ctx.message)))
        self._load_applications()
        logger.info("Listing all spotlight applications for {0.author!s} in {0.channel!s}"
            .format(ctx.message))

        # format each application as a string
        app_str_list = []
        for app in self.applications:
            if app.is_valid:
                app_str_list.append(app.discord_str())
            else:  # deleted entries: blank username/project name or blank user/'DELETED' project
                app_str_list.append(None)
                continue

        # format into a string list for display
        app_list_string = format_list(app_str_list) if app_str_list else 'Empty'
        # cleanup for deleted records
        # We don't have a dedicated column for this, so hacky regex post-numbering it is!
        app_list_string = re.sub(r'(^|\n)\s*\d+\. None(\n|$)', '\n', app_list_string)
        await self.send_embed_list(title=self.LIST_HEADING, contents=app_list_string)