PHP і фреймворки

HTTP-клієнт на PHP

Для продакшена лучше тонкий клиент на cURL, чем file_get_contents: видны HTTP-код, сетевые ошибки и проще ретраи.

Каркас клиента

final class TelegramClient
{
    public function __construct(
        private string $token,
        private int $timeout = 15,
    ) {}

    public function call(string $method, array $params = []): array
    {
        $ch = curl_init('https://api.telegram.org/bot' . $this->token . '/' . $method);
        curl_setopt_array($ch, [
            CURLOPT_POST           => true,
            CURLOPT_RETURNTRANSFER => true,
            CURLOPT_TIMEOUT        => $this->timeout,
            CURLOPT_HTTPHEADER     => ['Content-Type: application/json'],
            CURLOPT_POSTFIELDS     => json_encode($params, JSON_UNESCAPED_UNICODE),
        ]);
        $body = curl_exec($ch);
        $code = (int) curl_getinfo($ch, CURLINFO_HTTP_CODE);
        $err  = curl_error($ch);
        curl_close($ch);

        if ($body === false) {
            throw new RuntimeException('cURL: ' . $err);
        }
        $json = json_decode($body, true);
        if (json_last_error() !== JSON_ERROR_NONE) {
            throw new RuntimeException('JSON: ' . json_last_error_msg());
        }
        if ($code >= 400 || empty($json['ok'])) {
            $desc = $json['description'] ?? ('HTTP ' . $code);
            throw new RuntimeException('Telegram: ' . $desc);
        }
        return $json['result'];
    }
}

Что добавить в бою

  • логирование method + description без токена;
  • retry на 429 / 5xx с Truncated exponential backoff;
  • отдельный метод для multipart (sendDocument/sendPhoto с файлом).

Связка: webhook, sendMessage.