Создание платежа
Создаёт новый платёж в режиме RUB collect с выдачей реквизита для оплаты. После успешного ответа покажите клиенту данные из requisite; итоговый статус приходит в webhook.
POST https://api.protopays.io/api/v1/payments
Заголовки запроса
| Поле | Тип | Обяз. | Описание |
|---|---|---|---|
| Content-Type | string | да | Должен быть application/json. |
| X-Merchant-Secret | string | да | Секрет ключа из кабинета (как в настройках API). |
| Signature | string (hex) | да | HMAC-SHA256 от сырого тела запроса в UTF-8, hex в нижнем регистре. |
| X-Merchant-Key-Id | string | да | Публичный key_id строки API-ключа в кабинете. |
Подробнее: аутентификация.
Примеры запроса
curl
curl -X POST 'https://api.protopays.io/api/v1/payments' \
-H 'Content-Type: application/json' \
-H 'X-Merchant-Secret: <SECRET>' \
-H 'Signature: <SIGNATURE>' \
-d '{
"orderId": "order-001",
"amount": "1000",
"currency": "RUB",
"callbackUri": "https://example.com/hooks/protopays",
"method": "sbp"
}'Node.js (fetch)
Подставьте Base URL и секрет; тело для подписи должно совпадать с телом запроса байт в байт.
import crypto from "node:crypto";
const body = JSON.stringify({
orderId: "order-001",
amount: "1000",
currency: "RUB",
callbackUri: "https://example.com/hooks/protopays",
method: "sbp",
});
const secret = "<SECRET>";
const signature = crypto.createHmac("sha256", secret).update(body, "utf8").digest("hex");
const res = await fetch("https://api.protopays.io/api/v1/payments", {
method: "POST",
headers: {
"Content-Type": "application/json",
"X-Merchant-Secret": secret,
Signature: signature,
},
body,
});
console.log(res.status, await res.text());
Тело запроса (JSON)
Валидация соответствует серверным правилам: валюта только RUB; канал оплаты задаётся через rubCollect.method или корневое поле method (сервер мержит в rubCollect).
Обязательные поля
| Поле | Тип | Обяз. | Описание |
|---|---|---|---|
| orderId | string | да | Ваш идентификатор заказа, до 255 символов (trim). Идемпотентность — по связке с каналом. |
| amount | number | string | да | Сумма, минимум 1. Для RUB в ответе может форматироваться с двумя знаками. |
| currency | string | да | Только RUB для данного сценария. |
| callbackUri | string (URL) | да | HTTPS URL для webhook о смене статуса, до 2048 символов. |
| rubCollect | object | да | Обязателен объект; поле method внутри — канал (sbp, card и т.д. по enum). Альтернатива: передать method на корне тела. |
| rubCollect.method | string | да | Канал RUB collect, например sbp или card (см. OpenAPI enum). |
Необязательные поля
| Поле | Тип | Обяз. | Описание |
|---|---|---|---|
| method | string | нет | Дублирует rubCollect.method; удобно для плоского JSON. |
| description | string | нет | Описание, до 255 символов. |
| ratePercent | number | нет | Если поддерживается сценарием. |
| payer | object | нет | Вложенные payer.userId, payer.userIp — при необходимости. |
Ответ (успех)
HTTP 200. Корень содержит человекочитаемое message и объект data.
{
"message": "Payment created",
"data": {
"id": 1001,
"uuid": "550e8400-e29b-41d4-a716-446655440000",
"orderId": "order-001",
"status": "pending",
"amount": "1000.00",
"currency": "RUB",
"requisite": {
"type": "sbp",
"method": "sbp",
"value": "+79991234567",
"holder": "И. Иванов",
"bank": "Пример банк"
},
"expiresAt": "2026-04-20T15:30:00+00:00"
}
}Поля data
| Поле | Тип | Обяз. | Описание |
|---|---|---|---|
| id | number | да | Внутренний id платежа. |
| uuid | string (UUID) | да | Стабильный публичный идентификатор. |
| orderId | string | да | Тот же orderId, что в запросе. |
| status | string | да | Текущий статус (см. ниже). |
| amount | string | да | Сумма строкой (формат для RUB). |
| currency | string | да | RUB. |
| requisite | object | нет | Реквизит для оплаты; может отсутствовать, если выдача иная по сценарию. |
| expiresAt | string (ISO8601) | нет | Срок действия резерва реквизита. |
Статусы платежа
Значения status в API (основные): pending, completed, failed, cancelled, appeal. Точный набор и переходы — в OpenAPI и бизнес-логике.
Реквизиты (requisite)
Для СБП типично type / method указывают на сценарий, value — номер телефона или иной идентификатор; holder и bank — при наличии.
Подробнее: реквизиты — отдельная страница.
Webhook после создания
После смены статуса сервис отправит POST на callbackUri. Пример JSON и поля тела — в Webhook по платежу; повторы и тайминги — в Webhooks.
Срок жизни реквизита
Поле expiresAt в ответе задаёт момент истечения резерва; по истечении сценарий может потребовать нового платежа — уточняйте по статусам и webhook.
Идемпотентность
Повтор с тем же orderId и каналом возвращает тот же платёж. См. идемпотентность.
Полная машиночитаемая схема (OpenAPI JSON): /openapi/api-docs.json