From 786a306f296e8b7e9b4ae78ba6ee4aee23339398 Mon Sep 17 00:00:00 2001 From: Vladimir Bryzgalov Date: Fri, 17 Apr 2026 22:44:41 +0500 Subject: [PATCH] feat(telegram-client): sendMessage wrapper classifying permanent/transient errors --- includes/class-telegram-client.php | 76 ++++++++++++++++++++++++++++++ 1 file changed, 76 insertions(+) create mode 100644 includes/class-telegram-client.php diff --git a/includes/class-telegram-client.php b/includes/class-telegram-client.php new file mode 100644 index 0000000..8089d31 --- /dev/null +++ b/includes/class-telegram-client.php @@ -0,0 +1,76 @@ + $chat_id, + 'text' => $text, + 'parse_mode' => 'HTML', + 'disable_web_page_preview' => true, + ]; + if ($reply_markup !== null) { + $body['reply_markup'] = wp_json_encode($reply_markup); + } + + $url = 'https://api.telegram.org/bot' . $token . '/sendMessage'; + $response = wp_remote_post($url, [ + 'timeout' => 10, + 'body' => $body, + ]); + + if (is_wp_error($response)) { + throw new TelegramException('Network: ' . $response->get_error_message(), 0, false); + } + + $code = (int)wp_remote_retrieve_response_code($response); + $raw = (string)wp_remote_retrieve_body($response); + $data = json_decode($raw, true); + + if ($code === 200 && is_array($data) && !empty($data['ok'])) { + return $data; + } + + $desc = is_array($data) ? (string)($data['description'] ?? '') : ''; + $retry_after = 0; + if (is_array($data) && isset($data['parameters']['retry_after'])) { + $retry_after = (int)$data['parameters']['retry_after']; + } + + $permanent = self::is_permanent($code, $desc); + throw new TelegramException( + sprintf('HTTP %d %s', $code, $desc !== '' ? $desc : 'unknown error'), + $code, + $permanent, + $retry_after + ); + } + + private static function is_permanent(int $code, string $desc): bool + { + if ($code === 401 || $code === 403) return true; + if ($code === 400) { + $d = strtolower($desc); + if (strpos($d, 'chat not found') !== false) return true; + if (strpos($d, 'bot was blocked') !== false) return true; + if (strpos($d, 'user is deactivated') !== false) return true; + } + return false; + } +}