/v2/orders/{order_id}/refund
Запрос на возврат средств за заказ.
Метод является асинхронным.
Схема процесса возврата

Ограничения
Вы можете сделать полный или частичный возврат платежа.
Нельзя оформить возврат, если:
- сумма возврата меньше 1 рубля;
- после возврата в заказе останется меньше 1 рубля.
Возвраты доступны для платежей в одном из статусов paymentStatus:
CAPTURED— заказ успешно оплачен, средства списаны со счета плательщика;PARTIALLY_REFUNDED— совершен частичный возврат средств за заказ.
После успешного выполнения возврата статус платежа paymentStatus изменится:
- на
REFUNDED, если был произведен полный возврат; - на
PARTIALLY_REFUNDED, если после совершения возврата в заказе остались товары.
Сумма возвратов за текущий день будет удержана на следующий рабочий день из выплаты партнеру за заказ.
Пример: в вашем магазине совершен заказ на 1000 рублей и сделан возврат на 200 рублей. На следующий рабочий день вы получите выплату 800 рублей (1000 − 200).
Нельзя одновременно проводить несколько возвратов по одному заказу.
Перед отправкой повторного запроса проверьте, что текущая операция возврата завершена: status должен быть SUCCESS или FAIL.
Иначе вы получите ответ 409 Conflict c ошибкой ANOTHER_OPERATION_IN_PROGRESS.
Отслеживать изменения статуса возврата можно через нотификации /webhook, а также с помощью запросов:
Примеры проверки статуса возврата
С помощью метода /operations/{external_operation_id}/ по externalOperationId можно проверить состояние текущего возврата.
В примере ниже операция не завершена — "status": "PENDING". Нельзя отправить повторный запрос на возврат.
Пример ответа
{
"code": 200,
"status": "success",
"data": {
"operation": {
"operationId": "52b3c4a8-528b-45eb-a57f-8f808f65d28f",
"operationType": "REFUND",
"orderId": "OrderS-2038",
"amount": "250.00",
"pointsAmount": null,
"status": "PENDING", // возврат в процессе
"reason": null,
"params": { "motive": null, "branch_id": null, "manager_id": null },
"externalOperationId": "OrderS-2038",
"created": "2025-03-14T14:58:45.850206+03:00",
"updated": "2025-03-14T14:58:45.850206+03:00"
}
}
}
С помощью метода /operations/{external_operation_id}/ можно проверить все детали заказа.
В примере ниже операция возврата завершена успешно — "status": "SUCCESS", а платеж в статусе "paymentStatus": "PARTIALLY_REFUNDED". Можно отправить повторный запрос на возврат.
Пример ответа
{
"code": 200,
"status": "success",
"data": {
"operations": [
{
"operationId": "52b3c4a8-528b-45eb-a57f-8f808f65d28f",
"operationType": "REFUND",
"orderId": "OrderS-2038",
"amount": "250.00",
"status": "SUCCESS", // возврат успешно завершен
"reason": null,
"params": { "motive": null, "branch_id": null, "manager_id": null },
"externalOperationId": "OrderS-2038",
"created": "2025-03-14T14:58:45.850206+03:00",
"updated": "2025-03-14T14:58:46.084886+03:00",
"approvalCode": null
},
{
"operationId": "9c763cfb-dcf6-4056-be8f-ca9e2e61d772",
"operationType": "AUTHORIZE",
"orderId": "OrderS-2038",
"amount": "500.00",
"status": "SUCCESS",
"reason": null,
"params": {},
"externalOperationId": null,
"created": "2025-03-14T14:58:07.161667+03:00",
"updated": "2025-03-14T14:58:07.414886+03:00",
"approvalCode": null
}
],
"order": {
"currencyCode": "RUB",
"cart": {
"items": [
{
"productId": "p2",
"quantity": { "count": "1", "available": null, "label": null },
"type": "UNSPECIFIED",
"title": "Яндекс.Станция Мини",
"description": null,
"total": "250",
"subtotal": null,
"discountedUnitPrice": "250",
"unitPrice": null,
"measurements": null,
"receipt": null,
"finalPrice": "250",
"pointsAmount": null,
"features": null
}
],
"total": { "amount": "250", "pointsAmount": null, "label": null },
"cartId": "1eed9a9827e68ba8981d9961c1237624fabc19cda05044b574e06302e83c7549",
"externalId": null,
"coupons": null,
"discounts": null,
"measurements": null
},
"merchantId": "76cc0f5c-91c4-40f2-9794-64a64c3c6011",
"orderAmount": "250.00",
"orderId": "OrderS-2038",
"paymentMethod": { "methodType": "CARD", "cardLast4": "0412", "cardNetwork": "MASTERCARD" },
"shippingMethod": null,
"metadata": null,
"created": "2025-03-14T14:58:03.699930+03:00",
"updated": "2025-03-14T14:58:46.084886+03:00",
"paymentStatus": "PARTIALLY_REFUNDED", // платеж частично возвращен
"reason": null,
"paymentUrl": "https://`[`sandbox.pay.ya.ru`](http://sandbox.pay.ya.ru)`/l/I1RnP9",
"isPrepayment": false,
"splitCode": null
},
"delivery": null
}
}
Виды возвратов
Доступен полный или частичный возврат платежа.
Для выполнения полного возврата передайте только refundAmount, равный сумме заказа.
Для выполнения частичного передайте refundAmount, равный сумме возврата, и добавьте корзину предоставляемых товаров и услуг. Сформировать корзину можно одним из способов:
-
Способ 1: Указать состояние корзины после возврата.
Используйте поле
targetCart— целевая корзина, которая должна остаться у покупателя после выполнения возврата. Если это поле не указано, то считается, что корзина возвращается полностью.Поле
targetShippingприменимо только к Yandex Pay Checkout. В остальных случаях следует оставить это поле пустым. Если это поле не указано, то считается, что стоимость доставки возвращается полностью. -
Способ 2: Указать возвращаемые товары.
Используйте поле
refundCart— данные о возвращаемых позициях: количество единиц товара для возврата или сумма, на которую нужно уменьшить стоимость конкретного товара. Если поле не указано, возврат осуществляется на всю корзину.
Примечание
При использовании refundCart указывайте идентификатор операции externalOperationId. Он служит токеном идемпотентности и позволяет избежать риска повторных возвратов.
Примеры возвратов
Рассмотрим на примере заказа с orderId = Order-123 и следующей корзиной:
{
"items": [
{
"productId": "id-1",
"price": "50",
"title": "Шариковая ручка",
"quantity": {
"count": "10"
}
},
{
"productId": "id-2",
"price": "200",
"title": "Блокнот",
"quantity": {
"count": "2"
}
}
]
}
Полный возврат
http POST https://sandbox.pay.yandex.ru/api/merchant/v2/orders/Order-123/refund \
"Authorization: Api-Key ${API_KEY}" 'refundAmount:="900.00"'
Частичный возврат
Возврат единиц товара
Допустим, необходимо вернуть две шариковые ручки. Это делается следующим запросом:
http POST https://sandbox.pay.yandex.ru/api/merchant/v2/orders/Order-123/refund \
"Authorization: Api-Key ${API_KEY}" \
'targetCart[items][0]:={"productId": "id-1", "quantityCount": "8"}' \
'targetCart[items][1]:={"productId": "id-2", "quantityCount": "2"}' \
'refundAmount:="100.00"'
В этом примере:
- Количество шариковых ручек уменьшилось на 2, с 10 до 8 единиц.
- Поле
priceв запросе пропущено, но его вполне допустимо указать. quantityCountу позиции с блокнотом не изменилось, его можно было не указывать.
Возврат части денег
Допустим, необходимо вернуть 30 рублей за каждый из блокнотов. Это достигается путем уменьшения цены позиции.
http POST https://sandbox.pay.yandex.ru/api/merchant/v2/orders/Order-123/refund \
"Authorization: Api-Key ${API_KEY}" \
'targetCart[items]:=[{"productId": "id-1"}, {"productId": "id-2", "price": "170"}]' \
'refundAmount:="60.00"'
В этом примере:
- Цена блокнота уменьшилась на 30 рублей, с 200 до 170 рублей;
- Таким образом, производится возврат 60 рублей, поскольку блокнотов было два.
quantityCountне указаны, но вполне допустимо указать их прежние значения.
Возврат c указанием количества возвращаемого товара
Допустим, необходимо вернуть две шариковые ручки. Это делается следующим запросом:
http POST https://sandbox.pay.yandex.ru/api/merchant/v2/orders/Order-123/refund \
"Authorization: Api-Key ${API_KEY}" \
'refundCart[items][0]:={"productId": "id-1", "quantityCount": "2"}' \
'refundAmount:="100.00"'
В этом примере:
- Количество шариковых ручек уменьшилось на 2, с 10 до 8 единиц.
- Поле
priceв запросе пропущено, но его вполне допустимо было указать.
Возврат с указанием, какую часть от стоимости товара необходимо вернуть
Допустим, необходимо вернуть 30 рублей за каждый из блокнотов. Это достигается путем уменьшения цены позиции.
http POST https://sandbox.pay.yandex.ru/api/merchant/v2/orders/Order-123/refund \
"Authorization: Api-Key ${API_KEY}" \
'refundCart[items]:=[{"productId": "id-1"}, {"productId": "id-2", "price": "30"}]' \
'refundAmount:="60.00"'
В этом примере:
- Цена блокнота уменьшилась на 30, с 200 рублей до 170 рублей.
- Таким образом, производится возврат 60 рублей, поскольку блокнотов было два.
quantityCountне указаны, но вполне допустимо указать их прежние значения.
Ошибки при возврате
Пример
{
"status": "fail",
"reasonCode": "ORDERUPDATE_INVALID_ITEM_QUANTITY",
"reason": "Item with productId=\"123456\" has invalid quantity \"5\". Quantity expected to be between \"0\" and \"4\".",
"details": {
"min": "0",
"max": "4",
"actual": "5",
"product_id": "123456",
"description": "Item with productId=\"123456\" has invalid quantity \"5\". Quantity expected to be between \"0\" and \"4\"."
}
}
|
Name |
Description |
|
|
Type: string Статус операции возврата. |
|
|
Type: string Код ошибки. Указывает на конкретную причину ошибки. |
|
|
Type: string | null Текстовое описание ошибки. Может быть пустой строкой |
|
|
Type: object | null Объект с дополнительными данными об ошибке. Может быть пустым объектом |
Коды ошибок
Возможные значения reasonCode:
REFUND_AMOUNT_TOO_LARGE— Сумма возвратаrefundAmountпревышает доступный остаток для возврата.REFUND_AMOUNT_EXPECTATION_FAILED— Сумма возвратаrefundAmountне совпадает с фактической суммой на основе корзиныrefundCartилиtargetCartи стоимости доставкиtargetShipping.REFUND_ONLY_ONE_CART_EXPECTATION_FAILED— Одновременно переданы параметрыtargetCartиrefundCart. Используйте только один из них.REFUND_NOT_POSITIVE_AMOUNT— Сумма возвратаrefundAmountдолжна быть больше нуля.REFUND_NOT_POSITIVE_POINTS_AMOUNT— Сумма возврата баллов Плюса должна быть больше нуля. Баллы возвращаются пропорционально сумме возврата, проверьте валидность полейrefundAmount,priceиquantityCount.PARTIAL_REFUND_NOT_ALLOWED— Для текущего заказа частичный возврат не разрешен.INVALID_PAYMENT_STATUS— Текущий статус платежа не позволяет выполнить возврат. Смотрите разрешенные статусы в полеreason.EXTERNAL_AMOUNT_NOT_ALLOWED— ПолеexternalAmountнедоступно для вашего магазина. Для подключения обратитесь к менеджеру интеграции.REFUND_EXTERNAL_AMOUNT_EXCEEDED— Запрошенная суммаexternalAmountпревышает доступный остаток для возврата.ORDER_SHIPPING_MISMATCH— Данные о доставке в запросе не соответствуют исходному заказу (наличие доставки, тип доставки).ORDER_CART_EMPTY— Добавьте корзинуrefundCartилиtargetCart.ORDER_AMOUNT_MISMATCH— Общая сумма заказа не совпадает с суммой корзины и доставки, либо сумма корзины не равна сумме всех позиций.ORDER_CART_ITEM_ERROR— Некорректные данные в одной из позиций корзины.ORDER_CART_DATA_ERROR— Некорректные данные корзины.ORDER_CART_POINTS_ERROR— Невозможно корректно рассчитать сумму баллов Плюса с текущими параметрами. Проверьте валидность полейrefundAmount,priceиquantityCount.CART_DISCOUNTS_NOT_SUPPORTED— Версия корзины не поддерживает скидки. Для подключения обратитесь к менеджеру интеграции.SHARED_MERCHANTS_DUPLICATE_ORDERS— У магазинов, связанных по Merchant ID, найдено несколько заказов с одинаковым идентификатором.REFUND_AMOUNT_TOO_SMALL— Сумма возврата меньше минимальной. Минимальная сумма возврата — 1 рубль.REFUND_LEAVES_LESS_THAN_MINIMAL_AMOUNT— После возврата в заказе останется сумма меньше минимально допустимой. Минимальная сумма остатка — 1 рубль.ORDER_NOT_FOUND_ERROR— Заказ с указанным идентификатором не найден.ORDERUPDATE_INVALID_ITEM_PRICE_RANGE— Цена позиции вне допустимого диапазона.ORDERUPDATE_INVALID_ITEM_PRICE— Некорректная цена позицииprice.ORDERUPDATE_INVALID_ITEM_QUANTITY— Некорректное количество единиц товараquantityCount.ORDERUPDATE_INVALID_ITEM_TOTAL— Некорректная итоговая сумма возврата по позицииtotal.ORDERUPDATE_ITEM_TOTAL_EXPECTED— Не указана итоговая сумма возврата по позицииtotal.ORDERUPDATE_INVALID_ITEM_TOTAL_NON_ZERO— При нулевой ценеpriceили количествеquantityCountитоговая сумма позицииtotalдолжна быть равна нулю.ORDERUPDATE_INVALID_ITEM_PRICE_WITH_QUANTITY— Некорректное сочетание ценыpriceи количестваquantityCountдля возврата.ORDERUPDATE_INVALID_SHIPPING_PRICE— Стоимость доставки вне допустимого диапазона.ORDERUPDATE_DUPLIATE_ITEM_PRODUCT_ID— В корзине несколько позиций с одинаковымproductId.ORDERUPDATE_UNKNOWN_ITEM_PRODUCT_ID— Товар с указаннымproductIdотсутствует в исходной корзине заказа.ORDERUPDATE_UNABLE_TO_BALANCE_SEMIVALID_CART— Не удалось пересчитать корзину с частичной валидацией после применения возврата.
Request
POST
https://pay.yandex.ru/api/merchant/v2/orders/{order_id}/refund
Production
POST
https://sandbox.pay.yandex.ru/api/merchant/v2/orders/{order_id}/refund
Sandbox
Path parameters
|
Name |
Description |
|
order_id |
Type: string Уникальный идентификатор заказа на стороне продавца, который был передан в /orders при создании заказа. Max length: Example: `` |
Body
application/json
{
"branchId": "example",
"externalOperationId": "example",
"managerId": "example",
"extensions": null,
"motive": "example",
"refundAmount": "123.45",
"refundCart": {
"items": [
{
"price": "123.45",
"productId": "example",
"quantityCount": "123.45"
}
]
},
"refundExternalAmount": "123.45",
"targetCart": null,
"targetShipping": {
"amount": "123.45"
}
}
|
Name |
Description |
|
refundAmount |
Type: string<double> Сумма к возврату. Минимальная сумма возврата — 1 рубль. Example: |
|
branchId |
Type: string DEPRECATED Идентификатор точки продаж. Используйте поля из Max length: Example: |
|
extensions |
All of 1 type
Дополнительные параметры для оформления возврата Default: |
|
externalOperationId |
Type: string Идентификатор операции возврата в системе продавца. Должен быть уникальным. Передайте этот параметр, чтобы получить возможность отслеживать состояние операции возврата через метод operations/{external_operation_id}. Если операция не завершена (обрабатывается или остановлена), то повторный вызов метода возврата с такими же аргументами и таким же значением Если процесс возврата был успешно запущен, то повторный вызов метода возврата с тем же Max length: Example: |
|
managerId |
Type: string DEPRECATED Идентификатор менеджера. Используйте поля из Max length: Example: |
|
motive |
Type: string Причина возврата Max length: Example: |
|
refundCart |
All of 1 type
Описывает позиции корзины, которые нужно вернуть.
Не может быть указано одновременно с полем Example
|
|
refundExternalAmount |
Type: string<double> | null Сумма внешней оплаты, которую вы вернули покупателю (сертификаты, подарочные карты, баллы лояльности). Может быть не указана, равна 0 или больше 0. Ограничение: Не должна превышать значение Example: |
|
targetCart |
All of 1 type
Описывает итоговое состояние корзины после выполнения возврата.
Если это поле не указано, то считается, что корзина возвращается полностью.Не может быть указано одновременно с полем Example
|
|
targetShipping |
All of 1 type
Применимо только к Yandex Pay Checkout. В остальных случаях следует оставить это поле пустым. Описывает итоговое состояние доставки после выполнения возврата.
Если это поле не указано или равно Example
|
BillingReport
|
Name |
Description |
|
branchId |
Type: string Обязательное поле только для офлайн-магазинов. Идентификатор точки продаж Default: Max length: |
|
externalClientId |
Type: string Идентификатор клиента в системе продавца. Поле не должно содержать персональные данные Default: |
|
externalOperationId |
Type: string Идентификатор транзакции на стороне продавца Default: |
|
externalOperationTime |
Type: string Время транзакции на стороне продавца Default: |
|
ksoId |
Type: string Идентификатор терминала на стороне продавца Default: |
|
managerId |
Type: string Обязательное поле только для офлайн-магазинов. Идентификатор менеджера Default: Max length: |
Example
{
"branchId": "null",
"managerId": "null",
"ksoId": "null",
"externalClientId": "null",
"externalOperationId": "null",
"externalOperationTime": "null"
}
RefundExtensions
|
Name |
Description |
|
billingReport |
All of 1 type
Дополнительная информация для формирования отчета Example
|
Example
{
"billingReport": {
"branchId": "null",
"managerId": "null",
"ksoId": "null",
"externalClientId": "null",
"externalOperationId": "null",
"externalOperationTime": "null"
}
}
TargetCartItem
|
Name |
Description |
|
productId |
Type: string Идентификатор позиции в корзине на момент создания заказа. Если передать идентификатор, которого не было в первоначальной корзине — произойдет ошибка. Max length: Example: |
|
price |
Type: string<double> Цена одной единицы товара/услуги после выполнения операции. Необходимо указать, если цена одной единицы уменьшается в результате операции. Это может быть полезным, если необходимо вернуть часть денег за товар или подтверждении заказа. Если не указывать это поле в запросе, то считается, что цена осталась прежней. Example: |
|
quantityCount |
Type: string<double> Количество единиц товара для операции возврата. Значение зависит от используемой корзины:
Example: |
Example
{
"price": "123.45",
"productId": "example",
"quantityCount": "123.45"
}
TargetCart
|
Name |
Description |
|
items |
Type: TargetCartItem[] Example
|
Example
{
"items": [
{
"price": "123.45",
"productId": "example",
"quantityCount": "123.45"
}
]
}
TargetShipping
|
Name |
Description |
|
amount |
Type: string<double> Стоимость доставки после выполнения операции Example: |
Example
{
"amount": "123.45"
}
Responses
200 OK
Body
application/json
{
"code": 200,
"data": {
"operation": {
"amount": "123.45",
"created": "2025-01-01T00:00:00Z",
"externalOperationId": "example",
"operationId": "123e4567-e89b-12d3-a456-426614174000",
"operationType": "AUTHORIZE",
"orderId": "example",
"params": {},
"pointsAmount": "123.45",
"reason": "example",
"status": "PENDING",
"updated": "2025-01-01T00:00:00Z"
}
},
"status": "success"
}
|
Name |
Description |
|
code |
Type: unknown Default: |
|
data |
Type: OperationResponseData Example
|
|
status |
Type: string Default: Const: |
Operation
|
Name |
Description |
|
amount |
Type: string<double> Сумма операции в фиатной валюте Example: |
|
operationId |
Type: string<uuid> Max length: Example: |
|
operationType |
Type: string Enum: |
|
orderId |
Type: string Уникальный идентификатор заказа на стороне продавца. Используется:
Max length: Example: |
|
created |
Type: string<date-time> Дата и время создания операции (ISO 8601) Example: |
|
externalOperationId |
Type: string Идентификатор операции на стороне продавца Max length: Example: |
|
params |
Type: object Дополнительные параметры операции. Список полей отличается в зависимости от типа операции. При возврате сохраняются
При отмене сохраняется
Example
|
|
pointsAmount |
Type: string<double> Сумма операции в баллах Плюса Example: |
|
reason |
Type: string Причина ошибки Max length: Example: |
|
status |
Type: string Default: Enum: |
|
updated |
Type: string<date-time> Дата и время обновления операции (ISO 8601) Example: |
Example
{
"amount": "123.45",
"created": "2025-01-01T00:00:00Z",
"externalOperationId": "example",
"operationId": "123e4567-e89b-12d3-a456-426614174000",
"operationType": "AUTHORIZE",
"orderId": "example",
"params": {},
"pointsAmount": "123.45",
"reason": "example",
"status": "PENDING",
"updated": "2025-01-01T00:00:00Z"
}
OperationResponseData
|
Name |
Description |
|
operation |
Type: Operation Example
|
Example
{
"operation": {
"amount": "123.45",
"created": "2025-01-01T00:00:00Z",
"externalOperationId": "example",
"operationId": "123e4567-e89b-12d3-a456-426614174000",
"operationType": "AUTHORIZE",
"orderId": "example",
"params": {},
"pointsAmount": "123.45",
"reason": "example",
"status": "PENDING",
"updated": "2025-01-01T00:00:00Z"
}
}