import asyncio import logging from typing import Optional from discord.ext import commands from utils.news import ( fetch_rss, format_articles, RSS_URL_ARTICLES, RSS_URL_POSTS, truncate_message, ) logger = logging.getLogger(__name__) def _format_feed_section( data: Optional[list[dict]], author: str, label_warning: str, label_info: str, msg_error: str, msg_empty: str, title: str, link: str, ) -> str: """Форматировать один RSS-раздел (статьи или посты).""" if data is None: logger.warning( "%s: !nw — не удалось получить %s (API вернул None)", author, label_warning ) return msg_error elif data: return "\n".join(format_articles(data, title, link)) else: logger.info("%s: !nw — %s нет в RSS", author, label_info) return msg_empty class News(commands.Cog): """Команда !news — свежие статьи и новости по AI с Habr""" @commands.command(name="nw") async def nw(self, ctx: commands.Context) -> None: """Топ-5 свежих статей и новостей по AI с Habr""" articles, posts = await asyncio.gather( fetch_rss(RSS_URL_ARTICLES), fetch_rss(RSS_URL_POSTS), ) parts: list[str] = [ _format_feed_section( articles, str(ctx.author), "статьи", "статей", "Не удалось получить статьи.", "Статей пока нет.", "Лучшие статьи за сутки / Искусственный интеллект / Хабr", "https://habr.com/ru/hubs/artificial_intelligence/articles/top/daily/", ), _format_feed_section( posts, str(ctx.author), "посты", "постов", "Не удалось получить новости.", "Новостей пока нет.", "Лучшие новости за сутки / Искусственный интеллект / Хабr", "https://habr.com/ru/hubs/artificial_intelligence/news/top/daily/", ), ] message = truncate_message("\n".join(parts)) await ctx.send(message) logger.info( "%s: !nw выполнена (статей: %d, постов: %d)", ctx.author, len(articles) if articles else 0, len(posts) if posts else 0, )