From fe22e67b2b11cbbbdd04b7f1cf5d50fa8d0cea9b Mon Sep 17 00:00:00 2001 From: irondru Date: Wed, 1 Jul 2026 17:24:40 +0300 Subject: [PATCH] fix: use entities API for custom emoji with correct UTF-16 offsets --- bot_update_pinned_post.py | 29 +++++++++++++++++++---------- 1 file changed, 19 insertions(+), 10 deletions(-) diff --git a/bot_update_pinned_post.py b/bot_update_pinned_post.py index d3b5ed5..bd55357 100644 --- a/bot_update_pinned_post.py +++ b/bot_update_pinned_post.py @@ -86,12 +86,21 @@ def fetch_fear_and_greed() -> tuple[int, str]: raise FetchError(f"Fear and greed fetch failed: {exc}") from exc -def build_message(usd: float, btc: float, fng_value: int, fng_label: str) -> str: - return ( - f"💲 " - f"₽{usd:.2f} 💵 " - f"${btc:,.0f}".replace(",", " ") + f" 😱 {fng_value} ({fng_label})" - ) +def utf16_len(s: str) -> int: + return len(s.encode("utf-16-le")) // 2 + + +def build_message(usd: float, btc: float, fng_value: int, fng_label: str) -> tuple[str, list]: + usd_emoji = "💲" + btc_emoji = "💵" + btc_str = f"{btc:,.0f}".replace(",", " ") + prefix = f"{usd_emoji} ₽{usd:.2f} " + text = f"{prefix}{btc_emoji} ${btc_str} 😱 {fng_value} ({fng_label})" + entities = [ + {"type": "custom_emoji", "offset": 0, "length": utf16_len(usd_emoji), "custom_emoji_id": "5229186695072590160"}, + {"type": "custom_emoji", "offset": utf16_len(prefix), "length": utf16_len(btc_emoji), "custom_emoji_id": "5438436707164761151"}, + ] + return text, entities def post_telegram_ipv4(url: str, payload: dict, timeout: float = 10.0) -> dict: @@ -158,7 +167,7 @@ def post_telegram_ipv4(url: str, payload: dict, timeout: float = 10.0) -> dict: raise FetchError(f"Telegram IPv4 response JSON decode failed: {exc}") from exc -def edit_pinned_message(text: str) -> None: +def edit_pinned_message(text: str, entities: list) -> None: if not TELEGRAM_BOT_TOKEN or not TELEGRAM_CHAT_ID or not TELEGRAM_MESSAGE_ID: raise FetchError("Missing TELEGRAM_BOT_TOKEN, TELEGRAM_CHAT_ID or TELEGRAM_MESSAGE_ID in environment") @@ -167,7 +176,7 @@ def edit_pinned_message(text: str) -> None: "chat_id": TELEGRAM_CHAT_ID, "message_id": int(TELEGRAM_MESSAGE_ID), "text": text, - "parse_mode": "HTML", + "entities": entities, } try: with httpx.Client(timeout=10.0) as client: @@ -190,10 +199,10 @@ def main() -> int: usd = fetch_usd_rub() btc = fetch_btc_usd() fng_value, fng_label = fetch_fear_and_greed() - message = build_message(usd, btc, fng_value, fng_label) + message, entities = build_message(usd, btc, fng_value, fng_label) logging.info("Fetched values: USD/RUB=%s BTC/USD=%s FNG=%s (%s)", usd, btc, fng_value, fng_label) - edit_pinned_message(message) + edit_pinned_message(message, entities) logging.info("Pinned message updated successfully") return 0 except FetchError as exc: