Matching
Matching — сценарий, в котором вы заранее объявляете спрос на выплату, а платформа закрывает его входящими платежами. Вместо того чтобы выводить средства и отдельно принимать их обратно, вы сводите встречные потоки внутри платформы.
С точки зрения интеграции это не новый API, а режим работы уже знакомых методов POST /payment/pay-out и POST /payment/pay-in.
Как это работает
Заголовок раздела «Как это работает»- Вы создаёте заявку —
POST /payment/pay-outс флагомisMatching: true. - Заявка ждёт встречные платежи в состоянии «открыта».
- Ваши клиенты создают invoice-платежи —
POST /payment/pay-inс методомc2c_invoiceилиsbp_invoice. Платформа сама связывает их с подходящей заявкой. - Клиент подтверждает оплату на платёжной странице, загрузив чек.
- Когда сумма набрана, заявка закрывается, и вы получаете уведомление с
category: "matching".
Если набрать сумму не удалось, платформа сама создаёт обычную выплату на остаток.
Шаг 1. Создание заявки
Заголовок раздела «Шаг 1. Создание заявки»POST /payment/pay-out HTTP/1.1Host: https://svc.cashwell.ioContent-Type: application/jsonX-Secure-Key: <ваш API-ключ>
{ "amount": 15000, "merchantTransactionId": "txn_matching_001", "matchingTransactionId": "matching_001", "isMatching": true, "callbackUrl": "https://example.com/callback", "requisite": { "sbpNumber": "79991234567", "bank": "SBER", "ownerName": "Иван Иванов" }}| Поле | Обяз. | Описание |
|---|---|---|
isMatching | да | true — создать заявку вместо обычной выплаты |
amount | да | Сумма спроса |
merchantTransactionId | да | Ваш идентификатор операции |
matchingTransactionId | нет | Отдельный идентификатор заявки. Если не передан, используется merchantTransactionId |
requisite | да | Реквизиты, на которые уйдёт выплата |
Как определяется метод заявки
Заголовок раздела «Как определяется метод заявки»Поле method при создании заявки не передаётся — метод вычисляется по реквизиту:
Что передано в requisite | Метод заявки |
|---|---|
sbpNumber | sbp_invoice |
cardNumber | c2c_invoice |
Что происходит после создания
Заголовок раздела «Что происходит после создания»- обычная Pay-Out сделка не создаётся;
- создаётся matching-заявка;
- в ответ приходит объект в формате выплаты;
- заявка начинает принимать входящие invoice-платежи.
Шаг 2. Наполнение заявки
Заголовок раздела «Шаг 2. Наполнение заявки»POST /payment/pay-in HTTP/1.1Host: https://svc.cashwell.ioContent-Type: application/jsonX-Secure-Key: <ваш API-ключ>
{ "amount": 5000, "method": "sbp_invoice", "merchantTransactionId": "txn_payin_001", "payerInfo": { "ip": "203.0.113.45", "userId": "usr_847392" }}Связывание выполняется на нашей стороне: платформа ищет открытую заявку вашего кабинета с совместимым методом и, если находит, привязывает платёж к ней.
| Метод платежа | Подходящие заявки |
|---|---|
sbp_invoice | sbp, sbp_invoice |
c2c_invoice | c2c, c2c_invoice |
Шаг 3. Подтверждение оплаты
Заголовок раздела «Шаг 3. Подтверждение оплаты»Invoice-платёж не закрывается автоматически: клиент должен подтвердить оплату на платёжной странице, приложив чек. Это два публичных запроса, которые выполняет платёжная страница, а не ваш сервер.
Загрузка чека:
POST /file/trading/pay-in/invoice/upload/public?tradeId={tradeId}Возвращает uploadMetaKey. Принимается только PDF, до 5 МБ — формат проверяется и по расширению, и по содержимому файла.
Подтверждение:
POST /payment/public/{id}/confirmВ теле передаётся полученный uploadMetaKey. Этот вызов завершает пользовательскую часть сценария и отправляет сделку в дальнейшую обработку.
Если вы используете готовую платёжную страницу по ссылке paymentPageUrl, оба шага выполняются на ней сами — реализовывать их не нужно.
Fallback-поведение
Заголовок раздела «Fallback-поведение»В сценарии два независимых механизма подстраховки.
Заявки не нашлось. Pay-In пришёл с методом c2c_invoice или sbp_invoice, но подходящей открытой заявки нет. Запрос не отклоняется — платформа переводит его в обычный приём платежа:
| Запрошено | Станет |
|---|---|
sbp_invoice | sbp |
c2c_invoice | c2c |
Учитывайте это: метод в ответе может отличаться от метода в запросе.
Заявка не набралась вовремя. Если за отведённое время заявка закрылась не полностью, платформа автоматически создаёт обычную выплату на остаток суммы. Это делает фоновый процесс — отдельный вызов с вашей стороны не нужен.
Уведомления по заявке
Заголовок раздела «Уведомления по заявке»Состояние заявки приходит на тот же callbackUrl, но отличается от уведомления о сделке:
{ "category": "matching", "id": "3f1c9a70-3f6b-4a9e-9a10-2b7c4d5e6f70", "merchantTransactionId": "matching_001", "matchingTransactionId": "matching_001", "type": "pay-out", "status": "success_changed", "amount": 15000, "factFiatAmount": 14650, "crypto": "0", "rate": 0, "fee": "0", "tradeIdsAll": ["...", "..."], "tradeIdsSuccess": ["..."]}| Поле | Что означает |
|---|---|
category | matching — по нему отличайте эти уведомления от уведомлений о сделках |
id | Идентификатор заявки, не сделки |
amount | Сумма, которую вы заявили |
factFiatAmount | Сумма, фактически закрытая входящими платежами |
tradeIdsAll | Все сделки, привязанные к заявке |
tradeIdsSuccess | Только те, что закрылись успешно |
crypto, rate, fee | Всегда нули: заявка — контейнер, а не сделка |
Как состояние заявки отображается в status — в разделе Статусы сделок.
Postman-коллекция
Заголовок раздела «Postman-коллекция»Для быстрого прогона сценария есть готовая коллекция:
Она покрывает создание заявки, создание invoice-платежа, отмену, продление таймера, загрузку чека и подтверждение.
Перед запуском заполните переменные:
| Переменная | Значение |
|---|---|
baseUrl | Базовый URL API |
secureKey | Ваш API-ключ |
receiptFile | Абсолютный путь к файлу чека на вашей машине |
callbackUrl | Адрес для проверки webhook, если он нужен |
Остальные переменные — matchingId, payInTradeId, publicTradeId, uploadMetaKey — коллекция заполняет сама из ответов предыдущих запросов, поэтому выполнять запросы нужно последовательно сверху вниз.
Что дальше
Заголовок раздела «Что дальше»- Приём платежей (Pay-In) — параметры создания платежа
- Выплаты (Pay-Out) — параметры создания выплаты
- Статусы сделок — статусы заявок и сделок