Bot API

API монетизации Telegram-бота

Подключите бота к HiViews одним HTTP-запросом: отправляйте его, когда пользователь пишет боту, — и HiViews доставит ему подходящий рекламный пост. Вы зарабатываете на каждом показе.

POST https://hiviews.net/sendMessage

Как подключить бота

  1. Подключите бота в кабинете

    В веб-кабинете нажмите «Подключить бота» и вставьте токен из @BotFather. Токен передаётся по HTTPS, хранится в зашифрованном виде и больше нигде не показывается.

  2. Дождитесь модерации

    Мы проверим бота. Пока бот на модерации, API отвечает 403 The bot on moderation.

  3. Настройте показы

    Предложите тематики бота (их утверждает модерация), при желании отключите нежелательные категории рекламы и разрешите или запретите откровенные посты (в рамках правил Telegram). Язык рекламы подбирается автоматически по языку Telegram пользователя.

  4. Получите API-ключ

    Ключ показывается один раз — сразу после подключения бота; новый ключ можно выпустить в настройках бота в веб-кабинете. Храните его на сервере и не публикуйте в клиентском коде.

Запрос

POST https://hiviews.net/sendMessage с JSON-телом.

Заголовки

ЗаголовокЗначение
AuthorizationAPI-ключ как есть, без префикса Bearer
Content-Typeapplication/json

Поля тела

ПолеТипОписание
UserIdintID пользователя Telegram. Только личные чаты — группы и каналы не поддерживаются.
MessageIdintID сообщения пользователя — реклама придёт ответом на него.
UserFirstNamestring | nullИмя пользователя, подставляется вместо $name в тексте поста. Можно передать null — тогда возьмём имя из Telegram. $username в посте заменяется на @username зрителя (или имя, если username нет) — передавать его не нужно.
StartPlacebool, необязательноеtrue или отсутствует — приветственный показ, отправляйте при /start. false — обычный показ в других местах бота.

Пример тела

{
  "UserId": 123456789,
  "MessageId": 45,
  "UserFirstName": "Ivan",
  "StartPlace": true
}

Когда вызывать

  • Приветственный показ — первой строкой обработчика /start (StartPlace: true или без поля). Дождитесь ответа: при успехе API отвечает примерно через 2 секунды — пользователю даётся время прочитать рекламу, затем ваш бот показывает своё приветствие.
  • Обычный показ — в ответ на реальное действие пользователя (StartPlace: false), после того как бот выдал результат: сначала отправьте пользователю то, за чем он пришёл (видео, файл, ответ), и только затем запрашивайте рекламу. Так пост окажется последним сообщением в чате. Если реклама придёт до результата, результат сразу её перекроет: такие показы почти не кликают, и бот получает меньше рекламы с оплатой за переходы.
  • Правила одинаковы для ботов и мини-приложений (Mini Apps).

Лимиты частоты: пользователь получает не больше одной рекламы в час во всей сети (и не больше дневного лимита), а приветственный показ в одном боте — не чаще раза в сутки. Лишние вызовы просто вернут No posts found for this user.

Запросы разрешены только в личных чатах и только в ответ на реальный /start (первой строкой обработчика) или реальную активность пользователя.

Нельзя отправлять запросы без сообщения пользователя, отвечать на старые /start и подменять параметры (UserId, MessageId, StartPlace). За нарушения бот или мини-приложение блокируется, начисления отменяются; показы фейковым и пустым аккаунтам не оплачиваются.

Ответы

Тело ответа — простой текст, не JSON. Ориентируйтесь на HTTP-код и текст.

КодТекст ответаЧто означает
200Post sent!Рекламный пост отправлен пользователю. Ответ приходит примерно через 2 с — время на прочтение рекламы.
400No posts found for this userСейчас нет подходящей рекламы для этого пользователя. Это нормально — просто игнорируйте.
400JSON not found…Тело запроса пустое или не является JSON.
400"UserId" field not found…Не передано поле UserId.
400"MessageId" field not found…Не передано поле MessageId.
400"UserFirstName" field not found…Не передано поле UserFirstName (передайте хотя бы null).
400"Place" field not found…Не удалось определить место показа — проверьте поле StartPlace (bool).
400Chat type must be private (not group)Реклама отправляется только в личные чаты.
400API key not found…Нет заголовка Authorization или ключ неверный.
400Invalid BotFather token! (Refresh it in t.me/HiViewsBot)Токен бота отозван или изменён — обновите его в @HiViewsBot («Обновить токен» в карточке бота).
400Текст ошибки Telegram, например Forbidden: bot was blocked by the userTelegram отказал в отправке — чаще всего пользователь заблокировал бота.
403The bot on moderationБот ещё на модерации.
403The bot is blockedБот заблокирован — напишите в поддержку.
403The bot is disabled (enable in t.me/HiViewsBot)Показы выключены — включите их в веб-кабинете.

Примеры кода

curl -X POST https://hiviews.net/sendMessage \
  -H "Authorization: <API-ключ>" \
  -H "Content-Type: application/json" \
  -d '{
    "UserId": 123456789,
    "MessageId": 45,
    "UserFirstName": "Ivan",
    "StartPlace": true
  }'
Успешный ответ (≈2 с): 200 Post sent!

Подключение без токена

Если вы не хотите передавать токен бота, подключите бота в кабинете в режиме «Без токена». Вы подтверждаете, что бот ваш, кодом в его описании (Edit About в @BotFather), и получаете API-ключ. Дальше бот сам запрашивает рекламу и сам отправляет её пользователю.

  • Оплата — за подтверждённые показы и за переходы. Бот без токена сразу получает все кампании сети — приветственные и обычные показы, с оплатой за показы и за клики — и внешнюю рекламу; отдельного одобрения ждать не нужно. Оплачивается каждый показ, отправку которого подтвердил сам Telegram, поэтому отправляйте пост ровно в том виде, в каком получили. Переходы по рекламе с оплатой за клик — $0,04 за переход. Ставка за показ без токена ниже, чем с токеном: с токеном рекламу отправляем мы и подтверждение не требуется.
  • Запрос: POST https://hiviews.net/api/partner/ad с заголовком Authorization: API-ключ. Поля: UserId (обязательно), UserFirstName, Username, Language (язык пользователя из Telegram), StartPlace — true при /start, false после выдачи результата.
  • Ответ всегда JSON. Если реклама есть — "ok": true и объект ad: отправьте его пользователю как есть. Если рекламы нет — "ok": false, просто продолжайте работу.
  • Ничего не меняйте в посте. Ссылки в кнопках ведут через hiviews.net — по ним считаются переходы. Изменённая ссылка не оплачивается.
  • Подтверждение отправки. В начале текста стоит невидимая ссылка: когда бот отправляет пост, Telegram сам запрашивает её — так мы узнаём, что пост действительно ушёл. Поэтому не отключайте превью ссылок (disable_web_page_preview) и не вырезайте ссылки из текста. Неподтверждённый пост не оплачивается: ни показ, ни переходы по нему.
  • delete_after — если поле есть, удалите пост через столько секунд.
  • Переход на полный режим. Когда будете готовы, вставьте токен бота на его странице в кабинете. Код менять не нужно: тот же запрос продолжит работать, рекламу начнём отправлять мы (ответ будет без ad), и каждый показ будет оплачиваться по ставке с токеном, без подтверждения.
  • Защита от накрутки: все ссылки в рекламе идут через трекинг HiViews, и мы знаем, как часто по тем же кампаниям переходят в ботах с токеном. Бот, у которого переходы не сходятся с показами (намного меньше или намного больше ожидаемого), автоматически теряет оплачиваемые показы и возвращается к оплате только за переходы; бот, который на деле не отправляет большую часть взятых постов, перестаёт получать рекламу. Оплачивается не больше одного перехода с одного IP-адреса в час; при неправдоподобно высокой доле переходов оплата приостанавливается.
  • Сеть ботов. Полная инструкция — на странице «Сеть ботов». Если у вас много ботов, не нужно подключать каждый: по запросу в поддержку мы выдаём один ключ на всю сеть. Запрос тот же, плюс поле Bot — имя бота, для которого нужна реклама (без @): {"UserId": 123, "UserFirstName": "Ivan", "Language": "ru", "StartPlace": true, "Bot": "my_first_bot"}. Бот регистрируется при первом запросе, статистика ведётся по каждому боту и по сети целиком. Ответы bad_bot (имя не похоже на имя бота) и bot_taken (этот бот уже подключён кем-то отдельно) означают, что рекламу для этого имени получить нельзя.

Ответ

{
  "ok": true,
  "ad": {
    "text": "Ivan, look at this…",
    "parse_mode": "HTML",
    "reply_markup": {"inline_keyboard": [[{"text": "Open", "url": "https://hiviews.net/api/go/…"}]]},
    "photo": "https://hiviews.net/api/go/m/…",
    "delete_after": 60
  }
}

Готовый код: Python, aiogram 3

import asyncio, aiohttp
from aiogram import Bot
from aiogram.types import InlineKeyboardMarkup

HIVIEWS_KEY = "YOUR_API_KEY"

async def show_ad(bot: Bot, user, start: bool = False) -> None:
    payload = {"UserId": user.id, "UserFirstName": user.first_name, "Username": user.username,
               "Language": user.language_code, "StartPlace": start}
    try:
        async with aiohttp.ClientSession(timeout=aiohttp.ClientTimeout(total=5)) as s:
            async with s.post("https://hiviews.net/api/partner/ad", json=payload,
                              headers={"Authorization": HIVIEWS_KEY}) as r:
                ad = (await r.json()).get("ad")
        if not ad:
            return
        kw = {"parse_mode": "HTML", "reply_markup": InlineKeyboardMarkup.model_validate(ad["reply_markup"])}
        if ad.get("photo"):
            msg = await bot.send_photo(user.id, ad["photo"], caption=ad["text"], **kw)
        elif ad.get("video"):
            msg = await bot.send_video(user.id, ad["video"], caption=ad["text"], **kw)
        elif ad.get("animation"):
            msg = await bot.send_animation(user.id, ad["animation"], caption=ad["text"], **kw)
        else:
            msg = await bot.send_message(user.id, ad["text"], **kw)  # не отключайте превью ссылок
        if ad.get("delete_after"):
            asyncio.get_running_loop().call_later(
                ad["delete_after"], lambda: asyncio.ensure_future(quiet_delete(bot, user.id, msg.message_id)))
    except Exception:
        pass

async def quiet_delete(bot: Bot, chat_id: int, message_id: int) -> None:
    try:
        await bot.delete_message(chat_id, message_id)
    except Exception:
        pass

Готовый код: Node.js, Telegraf

// HiViews без токена: бот сам отправляет рекламу, оплата — за подтверждённые показы и переходы. Node.js 18+, Telegraf.
// Отправляйте пост как есть: по скрытой ссылке в тексте Telegram подтверждает нам отправку.
const HIVIEWS_KEY = "YOUR_API_KEY";

async function showAd(ctx, start = false) {
  // При /start вызывайте showAd(ctx, true), после выдачи результата — showAd(ctx, false).
  try {
    const u = ctx.from;
    const res = await fetch("https://hiviews.net/api/partner/ad", {
      method: "POST",
      headers: { Authorization: HIVIEWS_KEY, "Content-Type": "application/json" },
      body: JSON.stringify({ UserId: u.id, UserFirstName: u.first_name, Username: u.username,
                             Language: u.language_code, StartPlace: start }),
      signal: AbortSignal.timeout(5000),
    });
    const { ad } = await res.json();
    if (!ad) return; // сейчас рекламы для этого человека нет
    const extra = { parse_mode: "HTML", reply_markup: ad.reply_markup };
    let msg;
    if (ad.photo) msg = await ctx.telegram.sendPhoto(u.id, ad.photo, { caption: ad.text, ...extra });
    else if (ad.video) msg = await ctx.telegram.sendVideo(u.id, ad.video, { caption: ad.text, ...extra });
    else if (ad.animation) msg = await ctx.telegram.sendAnimation(u.id, ad.animation, { caption: ad.text, ...extra });
    else msg = await ctx.telegram.sendMessage(u.id, ad.text, extra); // превью ссылок не отключайте
    if (ad.delete_after) {
      setTimeout(() => ctx.telegram.deleteMessage(u.id, msg.message_id).catch(() => {}), ad.delete_after * 1000);
    }
  } catch (e) { /* реклама никогда не должна ломать бота */ }
}

// Пример:  bot.start(async (ctx) => { await showAd(ctx, true); /* ваше приветствие */ });

Готовый код: PHP

<?php
// HiViews без токена: бот сам отправляет рекламу, оплата — за подтверждённые показы и переходы.
// Отправляйте пост как есть: по скрытой ссылке в тексте Telegram подтверждает нам отправку.
const HIVIEWS_KEY = 'YOUR_API_KEY';

/** $user — массив from из апдейта Telegram. При /start: $start = true, после выдачи результата: false.
 *  Возвращает [message_id, delete_after] — если delete_after не null, удалите сообщение через столько секунд. */
function hiviews_show_ad(string $botToken, array $user, bool $start = false): ?array
{
    $ch = curl_init('https://hiviews.net/api/partner/ad');
    curl_setopt_array($ch, [
        CURLOPT_POST => true, CURLOPT_RETURNTRANSFER => true, CURLOPT_TIMEOUT => 5,
        CURLOPT_HTTPHEADER => ['Authorization: ' . HIVIEWS_KEY, 'Content-Type: application/json'],
        CURLOPT_POSTFIELDS => json_encode([
            'UserId' => $user['id'], 'UserFirstName' => $user['first_name'] ?? '',
            'Username' => $user['username'] ?? null, 'Language' => $user['language_code'] ?? null,
            'StartPlace' => $start,
        ]),
    ]);
    $ad = json_decode((string) curl_exec($ch), true)['ad'] ?? null;
    curl_close($ch);
    if (!$ad) {
        return null; // сейчас рекламы для этого человека нет
    }
    $params = ['chat_id' => $user['id'], 'parse_mode' => 'HTML', 'reply_markup' => json_encode($ad['reply_markup'])];
    if (!empty($ad['photo'])) {
        $method = 'sendPhoto'; $params += ['photo' => $ad['photo'], 'caption' => $ad['text']];
    } elseif (!empty($ad['video'])) {
        $method = 'sendVideo'; $params += ['video' => $ad['video'], 'caption' => $ad['text']];
    } elseif (!empty($ad['animation'])) {
        $method = 'sendAnimation'; $params += ['animation' => $ad['animation'], 'caption' => $ad['text']];
    } else {
        $method = 'sendMessage'; $params += ['text' => $ad['text']]; // превью ссылок не отключайте
    }
    $ch = curl_init('https://api.telegram.org/bot' . $botToken . '/' . $method);
    curl_setopt_array($ch, [CURLOPT_POST => true, CURLOPT_RETURNTRANSFER => true, CURLOPT_TIMEOUT => 10,
                            CURLOPT_POSTFIELDS => $params]);
    $sent = json_decode((string) curl_exec($ch), true);
    curl_close($ch);
    return [$sent['result']['message_id'] ?? null, $ad['delete_after'] ?? null];
}

// Пример:  hiviews_show_ad($botToken, $update['message']['from'], true);   // в обработчике /start

Советы

  • Вызывайте API первой строкой обработчика /start и дожидайтесь ответа (await). Успешный ответ приходит примерно через 2 секунды — это окно на прочтение рекламы; после него отправляйте своё приветствие.
  • Ставьте таймаут 5 секунд. При ошибке сети не повторяйте запрос — просто продолжайте работу бота.
  • Ответ 400 No posts found for this user приходит сразу — обрабатывайте его молча и показывайте приветствие.
  • Логируйте остальные ошибки: 403 требует действия в веб-кабинете, ошибка токена — в @HiViewsBot.
  • Храните API-ключ на сервере, в переменных окружения.

Доход и выплаты

  • $4,80 за 1000 приветственных и $2,40 за 1000 обычных показов.
  • $0,04 за переход — с рекламы, оплаченной за клики. Она идёт в бот, только если при его CTR это выгоднее показов. Интеграция та же: никаких изменений в API.
  • Доход становится доступен к выводу через 7 дней.
  • Вывод в USDT (TRC20) от $50, комиссия $3 — заявка в веб-кабинете, подтверждение в Telegram-боте.

или в Telegram-боте @HiViewsBot