TeleOpen Platform API
Backend-as-a-Service для продавцов VPN-подписок. Заводите серверы,
тарифы и подписки через REST API; отдавайте клиентам живые брендированные ссылки
teleopen://. Вы пишете только бота и приём оплаты — учёт, ротация
серверов, отзыв доступа и формат ссылки берёт на себя платформа.
Что это такое
Обычная ссылка-подписка (vless://, happ://) — это
замороженный конфиг. Сменили сервер — нужно перевыдавать ссылку всем клиентам.
Отозвать доступ у неплательщика нельзя.
teleopen:// — это указатель на управляемый объект на нашем бэке.
Содержимое живёт на сервере, поэтому:
- сменили ноду в пуле — у всех клиентов обновилось само, ссылка прежняя;
- клиент не продлил — мгновенный отзыв одним запросом;
- в ссылке живёт срок, остаток трафика, бренд продавца и кнопка «Продлить».
При этом та же ссылка отдаётся и в формате обычной подписки — её проглотит любой сторонний клиент (v2rayN, Happ и пр.), деградируя до простого списка серверов.
Модель данных
Каждый продавец — это изолированный tenant. Внутри своя зона:
Tenant (вы, продавец)
├── API-ключи — доступ бота к API
├── Nodes — серверы (vless/ss/trojan/hy2…)
├── Node Pools — группы нод («Европа», «для стриминга»)
├── Plans — тарифы (трафик / срок / устройства / пул)
└── Subscriptions — выданные клиентам подписки
└── teleopen:// — живая ссылка на каждую подписку
Аутентификация
Все машинные запросы — с заголовком:
Authorization: Bearer tlo_<ваш_api_ключ>
Ключ выпускается в личном кабинете (вход через Telegram) и показывается
один раз — мы храним только его хэш. Потеряли — выпустите новый, старый отзовите.
У ключа есть скоупы (sub:write, node:write, plan:write,
broadcast:send, analytics:read, …); по умолчанию выдаются все.
Быстрый старт за 4 запроса
Базовый URL: https://teleopen.space. Сценарий «клиент оплатил — выдать доступ»:
Завести серверы
Можно вывалить весь список разом — строки, base64-подписку или URL подписки:
curl -X POST https://teleopen.space/v2/nodes/import \
-H "Authorization: Bearer tlo_…" -H "Content-Type: application/json" \
-d '{"text":"vless://uuid@1.2.3.4:443#NL-1\nvless://uuid@5.6.7.8:443#DE-2"}'
→ {"imported": 2, "node_ids": ["53b2…", "22c4…"]}
Собрать пул и тариф
# пул из этих нод
curl -X POST …/v2/pools -H "Authorization: Bearer tlo_…" \
-d '{"name":"EU","node_ids":["53b2…","22c4…"]}'
→ {"id":"6aad…","name":"EU","strategy":"all", …}
# тариф: 100 ГБ, 30 дней, 3 устройства, пул EU
curl -X POST …/v2/plans -H "Authorization: Bearer tlo_…" \
-d '{"name":"Premium","traffic_limit":107374182400,
"duration_days":30,"device_limit":3,"pool_id":"6aad…"}'
→ {"id":"1537…", …}
Выдать подписку → получить ссылку
curl -X POST …/v2/subscriptions -H "Authorization: Bearer tlo_…" \
-d '{"plan_id":"1537…","external_user_id":"tg:55501",
"renew_url":"https://t.me/yourbot?start=renew"}'
→ {
"id": "ed53…", "status": "active",
"expires_at": 1783559423, "traffic_total": 107374182400,
"link": "teleopen://s/3zY8n5zGquEYMHnA",
"sub_url": "https://teleopen.space/v2/resolve/3zY8n5zGquEYMHnA?format=sub"
}
Отдайте link клиенту. Всё — продажа закрыта.
Управлять дальше
# продлить на 7 дней (ссылку перевыдавать НЕ нужно)
curl -X PATCH …/v2/subscriptions/ed53… -d '{"action":"extend","days":7}'
# мгновенно отозвать доступ
curl -X DELETE …/v2/subscriptions/ed53…
→ ссылка тут же отдаёт status:"banned", серверов нет
# у кого истекает в ближайшие 3 дня — для рассылки на продление
curl …/v2/subscriptions?expires_in=3d
Формат ссылки teleopen://
Короткий живой указатель:
teleopen://s/<code> напр. teleopen://s/3zY8n5zGquEYMHnA
code — 16 символов base62 (≈95 бит энтропии, не подбирается). Клиент,
открыв ссылку, обращается к резолверу за актуальным состоянием.
Резолвер
Параметр format выбирает представление:
format=json — для нативного клиента TeleOpen
{
"status": "active", // active|trial|expired|frozen|banned|exhausted
"subscription": {
"title": "Vasya VPN",
"expires_at": 1783559423, // unix, null = бессрочно
"traffic_total": 107374182400,
"traffic_used": 0,
"device_limit": 3,
"renew_url": "https://t.me/yourbot?start=renew"
},
"brand": { "name": "Vasya VPN", "color": "#0A84FF" },
"nodes": [ {"uri":"vless://…#NL-1"}, {"uri":"vless://…#DE-2"} ],
"update_interval": 360 // минут до следующего ре-резолва
}
format=sub — совместимый со сторонними клиентами
Отдаёт стандартную base64-подписку и заголовки profile-title,
subscription-userinfo (трафик/срок). Эту форму понимают любые
VPN-клиенты-подписчики — одна ссылка работает везде.
status и пустой список серверов, клиент отключается.Справочник: Tenant и ключи
Эти ручки — из личного кабинета (Telegram-вход), не по API-ключу.
Справочник: Ноды и пулы
Поддерживаемые схемы при импорте: vless vmess trojan ss ssr hysteria hysteria2 hy2 tuic.
По умолчанию каждый URI → отдельная нода; {"one_node":true} — все в одну.
Справочник: Тарифы
| Поле | Тип | Описание |
|---|---|---|
name | string | название (обязательно) |
traffic_limit | bytes | лимит трафика, null = ∞ |
duration_days | int | срок, null = бессрочно |
device_limit | int | лимит устройств |
pool_id | uuid | какой пул нод отдавать |
kind | string | standard|trial|promo|gift |
Справочник: Подписки
Действия PATCH ({"action": "…"})
| action | параметры | что делает |
|---|---|---|
extend | days | продлить срок |
add_traffic | bytes | добавить трафик |
freeze / unfreeze | — | заморозить / разморозить |
ban | — | забанить |
change_plan | plan_id | сменить тариф |
reset_devices | — | сбросить привязки устройств |
set_renew_url | renew_url | ссылка на продление |
Фильтры GET /v2/subscriptions
| параметр | пример | описание |
|---|---|---|
status | active | по статусу |
plan_id | uuid | по тарифу |
expires_in | 3d · 24h | истекают в окне — для рассылок |
Ошибки и лимиты
| код | значение |
|---|---|
400 | неверные параметры запроса |
401 | нет/неверный/отозванный API-ключ |
402 | достигнут лимит подписок вашего тарифа платформы |
403 | не хватает скоупа или tenant приостановлен |
404 | объект не найден (в т.ч. чужой — изоляция tenant'ов) |
429 | превышен rate-limit |
Тело ошибки: {"detail": "описание"}. Все объекты строго изолированы по
tenant'у — чужие подписки/ноды недоступны (возвращается 404).
Что дальше (roadmap)
Ядро (ноды, пулы, тарифы, подписки, живые ссылки) — работает. В разработке:
- Devices & anti-sharing — лимит и контроль устройств на подписку;
- Webhooks — события (истекает / превышен трафик / новое устройство) в вашего бота;
- Коннектор 3x-ui / Marzban — подключение готовых панелей по API-токену;
- Broadcast — пуш-рассылка прямо в приложение по сегменту подписчиков;
- Брендированная сборка APK — своё имя/иконка/схема ссылки;
- Аналитика — MAU, churn, нагрузка нод;
- SDK (Python/JS), готовый open-source шаблон Telegram-бота.