Перейти к основному содержимому

История изменений API

Изменения в публичном API и в поведении методов верификации. Новые записи — сверху.

30.10.2026​

Изменено​

  • Русские подписи методов в справочниках. pass_call теперь «Голосовой код» вместо «Голосовое подтверждение», sms — «СМС», mts_id — «МТС ID», max_otp — «MAX — код», max_bot — «MAX — бот». Значения не изменились — поменялись только подписи в GET /meta, GET /config и GET /meta/dictionaries/methods.

  • Цены входов через VK ID и Яндекс ID — в GET /dashboard/prices. Появился список providers с ценой за подтверждённый вход. В GET /v1/prices его нет намеренно: такой вход нельзя запросить через POST /v1/verify, он происходит внутри размещённой страницы входа, а включается в настройках клиента. Показывать его в публичном прайсе значило бы рекламировать метод, который API откажется принять.

    Провайдер без установленной цены в списке не появляется — он работает и бесплатен.

  • У методов в справочниках появилось описание. Каждый элемент methods несёт поле description — одно предложение о том, что метод делает. Этого хватает, чтобы нарисовать выбор метода целиком по ответу API, не храня тексты у себя.

    «Голосовое подтверждение» не говорило главного: пользователю придёт код, который нужно ввести. В списке методов это и есть ключевое различие — reverse_flash_call подтверждает без кода, pass_call с кодом.

29.10.2026​

Добавлено​

  • Справочники значений — чтобы не держать их копию у себя. GET /meta/dictionaries отдаёт список доступных справочников, GET /meta/dictionaries/{name} — один из них: значения ровно в том виде, в каком их присылает API, и подписи на языке запроса (Accept-Language). Авторизация не нужна.

    Справочники называются так же, как поля, которые описывают: значение поля operator ищется в operators, status — в statuses. Ответы кэшируются на час.

    Зачем: таблица подписей, живущая в коде фронтенда, расходится с API молча — и ломается как раз на значениях, добавленных последними.

28.10.2026​

Исправлено​

  • QR для оплаты с телефона снова открывается. На странице пополнения баланса код мог не загрузиться и отдавал ошибку. Теперь он строится на нашей стороне и доступен для пополнений картой, через СБП и T-Pay.

    Для SberPay кода нет: ссылка этого способа открывается нажатием на том же устройстве, а камера телефона её не распознаёт. На странице остаётся кнопка оплаты.

Изменено​

  • Новый аккаунт открывается после проверки. Регистрация в кабинете теперь создаёт аккаунт в статусе «на проверке»: вход в кабинет и ключи доступны сразу, а POST /v1/verify и остальные методы API отвечают 401, пока аккаунт не подтвердят. Обычно это занимает рабочий день; если нужно быстрее — напишите на support@verificahub.ru.

    Существующие аккаунты не затронуты: проверка применяется только к новым регистрациям.

  • Ключи и состояние аккаунта в ответах 401 теперь различимы. Раньше неверный секрет и закрытый аккаунт выглядели одинаково, и можно было часами искать ошибку в учётных данных, которой нет. Текст ответа теперь говорит, в чём дело.

  • Поле «сайт» принимает только главный домен. https://your-company.com — да, https://your-company.com/account/requests — нет, как и адрес с параметрами из рекламной ссылки. Проверка работает при регистрации и при изменении профиля.

Добавлено​

  • Новый метод pass_call — подтверждение голосом. Робот звонит на номер и диктует код, пользователь вводит его в POST /v1/verify/check, как при sms. Код не передаётся сообщением, поэтому его нельзя перехватить из уведомления на заблокированном экране.

    { "phone_number": "+79161112233", "method": "pass_call" }

    Тарифицируется в момент запроса, а не по факту ответа: звонок заказывается у оператора платно независимо от того, снял ли абонент трубку. Неотвеченный вызов возвращает failed, но списание уже произошло — это отличие от обратного звонка, где вы платите только за успешное подтверждение.

    Звонок приходит с маркировкой «ИП Iskuzhin IT» — требование закона к звонкам от юридических лиц, подставить название вашего сервиса нельзя. Предупредите об этом на экране ожидания: пользователь увидит звонок от незнакомого ему имени.

    Метод доступен по заявке. Если он закрыт вашему аккаунту, POST /v1/verify ответит 403 с error_code: method_not_available. Если метод вообще не подключён на платформе — 400 с error_code: validation_error. Это два разных случая, и различать их стоит: первый решается заявкой, второй значит, что метода пока нет ни у кого.

27.10.2026​

Исправлено​

  • POST /v1/verify больше не отклоняет подтверждения с 402 no_gateway_available из-за суточного ограничения на нашей стороне. В дни с высокой нагрузкой встроенный суточный бюджет выдач мог исчерпаться задолго до конца суток, и дальнейшие запросы отклонялись, хотя подтверждение было выполнимо. Ограничение снято. Код no_gateway_available остаётся — но теперь он означает, что доставку действительно нельзя выполнить, а не что на сегодня исчерпан лимит.

    Повторять запрос после этой ошибки по-прежнему имеет смысл: причины, по которым она возникает, как правило краткосрочные.

22.10.2026​

Изменено​

  • GET /v1/prices и GET /dashboard/prices: у каждого метода появилось поле available. Тариф остаётся в списке вместе с ценой, а available говорит, доступен ли метод вашему аккаунту. У аккаунта без ограничений во всех строках true.

    {
    "prices": [
    { "method": "mts_id", "price": { "amount": 2.50, "currency": "RUB" }, "available": true },
    { "method": "sms", "price": { "amount": 3.00, "currency": "RUB" }, "available": false }
    ]
    }

Добавлено​

  • В SMS теперь указаны адрес вашего сайта и название — как в max_otp. Получатель видит, чей это код:

    1057 - Vash kod podtverzhdeniya na resurse partnyora https://example.ru (Primer)

    Название берётся из профиля аккаунта, а если заполнены реквизиты — к нему добавляется наименование организации. Текст остаётся латиницей и укладывается в одно SMS, поэтому цена метода не меняется.

  • Новый код ошибки: 403 method_not_available. Возвращается POST /v1/verify, если метод сейчас недоступен вашему аккаунту; в detail перечислены методы, которые доступны. Это то же правило, что и available в списке тарифов, — список и то, что принимает /v1/verify, всегда совпадают. На уже настроенные у вас методы это не влияет: ограничение задаётся на аккаунт, а не вводится задним числом.

  • method_policy.steps у клиентов подтверждения телефона проверяется при сохранении. Шаг с методом, недоступным аккаунту, отклоняется с тем же 403 method_not_available при создании и при изменении клиента — вместо того чтобы молча выпасть из цепочки во время входа.

07.10.2026​

Добавлено​

  • max_otp — новый метод подтверждения: код приходит сообщением в MAX. 2,00 ₽. Открывать ничего не нужно — ни ссылку, ни бота, ни приложение: сообщение просто приходит, как SMS. Пользователь вводит код в POST /v1/verify/check, как в sms.

    POST /v1/verify
    { "method": "max_otp", "phone_number": "+79991234567" }

    В сообщении указаны адрес вашего сайта и название — чтобы получатель видел, чей это код:

    2483 - ваш код подтверждения на ресурсе партнера https://example.ru (Пример (c) ООО «Пример»)

    Название берётся из названия аккаунта, а за ним добавляется юридическое наименование из реквизитов, если они заполнены. Проверьте в личном кабинете, что там записано то, что вы хотите показывать людям.

    Списывается при отправке: доставка синхронная, и ответ приходит уже после неё. Если номера нет в MAX, подтверждение не создаётся и деньги не списываются — 422, как при любой другой недоставке.

    max_bot остаётся и в шесть с лишним раз дешевле — 0,30 ₽ против 2,00 ₽. Это два разных метода, а не замена: в max_bot пользователь открывает бота по ссылке и делится номером, в max_otp не делает ничего. Выбор между ними — обмен цены на этот шаг.

  • Проверка номера — две новые услуги. Отдельно от подтверждений: проверка не доказывает владение номером, а достаёт сведения о самом номере.

    • POST /v1/lookup/number-info — оператор, регион и был ли номер перенесён. 0,80 ₽
    • POST /v1/lookup/activity — насколько номер активен в сети, от 0 до 1. 1,50 ₽

    Обе работают по номерам любых операторов РФ. Ответ всегда содержит cost — ровно то, что списано; по нему и сверяйте счёт.

    «Нет данных по номеру» — это тоже ответ, а не ошибка: придёт 200 со status: "no_data". За такой ответ мы не списываем, как и за номер вне зоны обслуживания услуги. Ошибкой остаётся только то, что ошибка и есть: неверный формат номера (400), нехватка средств (402), недоступность услуги (503).

  • Проверка номеров списком — в личном кабинете. Загрузите файл с номерами (CSV или просто по номеру на строку) и получите результат файлом; до 50 000 номеров за раз.

    Проверку выбираете вы — активность номера или сведения о номере. Цена та же, что и за одиночную проверку; скорость разная: список на активность считается целиком и быстро, а сведения о номере собираются по одному номеру, поэтому большой список — это часы, а не минуты.

    Платите за номера, по которым пришёл ответ. Номер без ответа не считается — то же правило, что и для одиночной проверки. Баланс проверяется до запуска: задание, которое нечем оплатить, не начинается наполовину. Задание, которое не доехало, не стоит ничего.

    Повторы в файле считаются один раз. Строки, которые не являются проверяемым номером, в задание не попадают и возвращаются вам с номерами строк — заголовок файла в том числе.

    Результат доступен для скачивания ограниченное время: в файле ваши номера, и дольше нужного мы их не храним.

  • Тарифы на проверку номеров — в GET /v1/prices. Рядом с prices появился список lookups. Это два разных списка, и смешивать их не надо: подтверждение тарифицируется по своему событию (отправка, попытка или успех — смотря какой метод), проверка — за ответ. Услуга без действующего тарифа в список не попадает.

  • Потребление проверок — в GET /v1/usage. Новый блок lookups:

    "lookups": {
    "total": 40,
    "billable": 37,
    "total_cost": { "amount": 31.10, "currency": "RUB" },
    "by_method": { "number_info": 25, "activity_score": 15 },
    "by_status": { "ok": 37, "no_data": 3 }
    }

    Верхние поля отчёта по-прежнему только о подтверждениях — проверки в них не входят. Потрачено за период = total_cost + lookups.total_cost. billable — за сколько запросов списано; меньше total ровно на те, где данных по номеру не нашлось.

  • Услуги проверки — в справочниках GET /meta и GET /config: отдельный список lookups, плюс в /config словари lookup_statuses и bulk_lookup_statuses.

Изменено​

  • Проверки номеров входят в акт и детализацию. В сумме акта они учитываются вместе с подтверждениями, а в детализации у них свой лист «Проверки номеров»: одиночная проверка — строкой с маскированным номером, пакетная — одной строкой с названием файла и числом оплаченных номеров. В сводке итог разбит на «за подтверждения» и «за проверки номеров».

    Суммы в актах за прошлые периоды не пересчитываются.

  • max_bot в справочниках теперь называется «MAX Bot», а «MAX» — это max_otp. Раньше оба метода выводились как «MAX», и выбрать нужный по названию было нельзя. Значения (max_otp, max_bot) не изменились — поменялись только подписи в GET /meta и GET /config.

Исправлено​

  • Проверка активности отвечала 503 вместо «нет данных». Если по номеру нет оценки активности, POST /v1/lookup/activity возвращал 503 lookup_unavailable — то есть «попробуйте позже» для запроса, ответ на который не изменится. Теперь приходит обещанное: 200 со status: "no_data" и cost = 0.

    Повторять такой запрос смысла нет: по этому номеру у оператора оценки активности нет. «Сведения о номере» по тому же номеру при этом могут ответить — это свойство услуги, а не номера, так что проверить номер другой услугой имеет смысл.

  • Пакетная проверка активности: первый номер списка не проверялся, а в счёт попадали номера без ответа. Задание выглядело выполненным, но в результате не хватало первой строки, а стоимость считалась по числу обработанных номеров, а не по числу полученных ответов.

    Теперь платите только за номера, по которым пришёл ответ — то же правило, что и для одиночной проверки. В задании видны оба числа: numbers_processed — сколько номеров обработано, numbers_billed — сколько из них оплачено.

    Задания, выполненные до исправления, стоит запустить заново: в их результате не хватает первой строки. Если по такому заданию списано больше, чем в нём ответов, напишите — вернём разницу.

02.10.2026​

Исправлено​

  • Скачивание PDF счёта в личном кабинете. Кнопка скачивания счёта на оплату возвращала ошибку — файл не выгружался. Исправлено: счёт скачивается и приходит с понятным названием («Счет № 3 от 29.09.26.pdf» вместо «invoice-3.pdf»).

    Кроме того, счёт теперь сохраняется у нас при выставлении и остаётся доступным для скачивания 30 дней — независимо от того, сколько живёт ссылка на файл. Если счёт нужен для бухгалтерии дольше, скачайте и сохраните его у себя в течение этого срока.

01.10.2026​

Добавлено​

  • Кредитный лимит: допустимый отрицательный остаток. Для аккаунтов, с которыми это согласовано договором, подтверждения продолжают работать, когда баланс уходит в минус, — до согласованной границы. Остальные аккаунты работают как раньше: подтверждения останавливаются на нулевом балансе.

    В GET /v1/balance добавлены два поля:

    • credit_limit — насколько ниже нуля может уйти баланс, или null, если нельзя;
    • available — сколько фактически осталось потратить: balance + credit_limit.

    Ориентируйтесь на available, а не на balance. Запрос дороже available отклоняется с insufficient_balance (402) — как и раньше, код ошибки не изменился. У аккаунта с кредитным лимитом balance может быть отрицательным, и само по себе это не ошибка.

    Письмо о низком балансе теперь тоже считается от остатка возможностей, а не от нуля: аккаунт с лимитом получает предупреждение, когда приближается к своей границе, а не когда баланс проходит ноль.

29.09.2026​

Добавлено​

  • Детализация к ежемесячному акту. К акту об оказанных услугах теперь прилагается детализация за отчётный период в формате .xlsx — четыре листа: сводка, разбивка по методам подтверждения, разбивка по дням и построчный перечень оплаченных подтверждений с датой, маскированным номером, методом, статусом и суммой. Скачивается в личном кабинете, ссылка приходит вместе с актом.

    Суммы считаются по фактически списанным средствам, поэтому итог детализации сходится с суммой акта. В перечень попадает всё, за что списаны деньги, — включая подтверждения, которые не завершились успехом: SMS тарифицируется за отправку, «Мобильный ID» — за попытку, поэтому оплаченные строки со статусом «Истекло» и «Неуспешно» в перечне есть и это ожидаемо. В сводке такие подтверждения выделены отдельной строкой, а лист «По статусам» показывает их разбивку.

    Подтверждения, за которые деньги не списывались, в перечень не попадают, но их количество указано в сводке строкой «Не тарифицировано» — чтобы картина за период была полной.

26.09.2026​

Добавлено​

  • Причина неуспешной верификации. GET /v1/verify/{request_id} и список верификаций в личном кабинете теперь возвращают failure_reason для завершившихся неуспехом проверок: no_response (никто не отреагировал до истечения срока), declined (абонент отказался), wrong_code (закончились попытки ввода), not_delivered (код или звонок не дошли), unreachable (номер недоступен для этого метода), unknown. Набор значений фиксированный — на него можно опираться в коде. В списке верификаций по нему можно фильтровать (?filter=failure_reason==not_delivered).

  • Свой порог уведомления о низком балансе. В PUT /dashboard/account появилось поле low_balance_threshold — баланс, при достижении которого мы пишем на почту владельца аккаунта. Раньше порог был единым для всех (100 ₽), и изменить его было нельзя. Пустое значение означает «использовать значение по умолчанию», 0 — отключить уведомление. В ответе возвращаются и ваше значение, и фактически действующий порог (effective_low_balance_threshold).

Исправлено​

  • Повторное уведомление о низком балансе. Если баланс уже был ниже порога, письмо больше не приходило — независимо от того, насколько он опускался дальше. Теперь уведомление отправляется один раз при уходе баланса ниже порога и снова становится активным после пополнения.

24.09.2026​

Изменено​

  • Принимаются только российские мобильные номера. POST /v1/verify теперь отвечает 400 region_not_supported, если номер не является мобильным номером РФ (+79…). Раньше принимался любой номер из одиннадцати цифр, начинающийся с 7: в эту проверку проходили номера Казахстана и Абхазии, городские номера и опечатки вида 8890…, которые после нормализации выглядели как +7890…. Доставить на такие номера невозможно, и ни одна подобная верификация ни разу не была подтверждена — теперь запрос отклоняется сразу, без создания верификации и без списания.

21.09.2026​

Исправлено​

  • mts_id, абоненты Tele2 и МегаФон. Подтверждение по SMS-коду завершалось ошибкой, и верификация истекала, даже если код был введён верно. Метод работает штатно для всех операторов.
  • Повторная отправка уже принятого кода больше не расходует попытку. Если оператор уже принял код, повторный POST /v1/verify/check возвращает 409 not_pending вместо 400 invalid_code, и попытка не списывается.
  • Событие verification.failed теперь отправляется на ваш webhook-адрес и для метода mts_id. Раньше исчерпание попыток по этому методу было видно только через GET /v1/verify/{request_id}.

Важно для интеграторов​

  • В методе mts_id код вводится только на этапе SMS-OTP — он используется, когда подтверждение через SIM-push недоступно. На этапе SIM-push вводить нечего, и POST /v1/verify/check вернёт 409 not_pending.
  • На этапе SMS-OTP ответ 200 означает, что код принят оператором; в теле ответа статус остаётся sent. Итог приходит событием verification.verified (обычно в пределах секунды) либо доступен через GET /v1/verify/{request_id}.

Биллинг​

  • Выполнен перерасчёт по верификациям, затронутым техническими проблемами на нашей стороне. Средства возвращены на баланс, затронутые интеграторы уведомлены.