QIWI Checkout API
Edit on GitHub
QIWI Checkout API opens a way to operations with invoices from your service or application. Invoice is the unique request for the payment. The user may pay the invoice with any accessible means. API supports issuing and cancelling invoices, making refunds and checking operation status.
To use API, you need public and secret keys. Keys are available after registration and integration on kassa.qiwi.com or p2p.qiwi.com.
Invoicing Operations Flow
-
User submits an order on the merchant’s website.
-
Merchant redirects the user to Payment Form link to issue an invoice for the order and to make the user pay for it. Or issues an invoice by API and redirects to the Payment Form.
-
The user chooses the most convenient way to pay for the invoice on the Payment Form. By default, the optimal payment method is showed first.
-
The merchant's service receives notification once the invoice is successfully paid by the user. You need to configure notifications on your Personal Page. Notifications contain authorization parameters which merchant needs to verify on its server.
- If needed, via Bill Payments REST API merchant can:
- request current status of the invoice,
- cancel invoice (if the user has not initiated payment yet).
- When the invoice payment is confirmed, merchant delivers ordered services/goods.
Authorization
API requests from the merchant's side are authorized by the API secret key (SECRET_KEY
). Put this parameter to Authorization header, as "Bearer SECRET_KEY".
Public key (PUBLIC_KEY
) is used when issuing invoices via the Payment Form.
Keys are available after registration and integration kassa.qiwi.com or p2p.qiwi.com .
const QiwiBillPaymentsAPI = require('bill-payments-node-js-sdk');
const SECRET_KEY = 'eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjUyNjgxMiwiYXBpX3VzZXJfaWQiOjcxNjI2MTk3LCJzZWNyZXQiOiJmZjBiZmJiM2UxYzc0MjY3YjIyZDIzOGYzMDBkNDhlYjhiNTnONPININONPN090MTg5Z**********************';
const qiwiApi = new QiwiBillPaymentsAPI(SECRET_KEY);
--header "Authorization: Bearer MjMyNDQxMjM6NDUzRmRnZDQ0M*******"
<?php
const SECRET_KEY = 'eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjUyNjgxMiwiYXBpX3VzZXJfaWQiOjcxNjI2MTk3LCJzZWNyZXQiOiJmZjBiZmJiM2UxYzc0MjY3YjIyZDIzOGYzMDBkNDhlYjhiNTnONPININONPN090MTg5Z**********************';
/** @var \Qiwi\Api\BillPayments $billPayments */
$billPayments = new Qiwi\Api\BillPayments(SECRET_KEY);
?>
String secretKey = "eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjUyNjgxMiwiYXBpX3VzZXJfaWQiOjcxNjI2MTk3LCJzZWNyZXQiOiJmZjBiZmJiM2UxYzc0MjY3YjIyZDIzOGYzMDBkNDhlYjhiNTnONPININONPN090MTg5Z**********************";
BillPaymentClient client = BillPaymentClientFactory.createDefault(secretKey);
var secretKey = "eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjUyNjgxMiwiYXBpX3VzZXJfaWQiOjcxNjI2MTk3LCJzZWNyZXQiOiJmZjBiZmJiM2UxYzc0MjY3YjIyZDIzOGYzMDBkNDhlYjhiNTnONPININONPN090MTg5Z**********************";
var client = BillPaymentClientFactory.createDefault(secretKey);
1. Invoice Issue by API
It is the reliable method for integration. Parameters are sent by means of server2server requests with authorization. Method allows you to issue an invoice, successful response contains payUrl
link to redirect client on Payment Form.
Request → PUT
HEADERS
- Authorization: Bearer SECRET_KEY
- Accept: application/json
- Content-Type: application/json
const billId = '893794793973';
const fields = {
amount: 1.00,
currency: 'RUB',
comment: 'Hello world',
expirationDateTime: '2018-03-02T08:44:07'
};
qiwiRestApi.createBill( billId, fields ).then( data => {
//do smth with data
});
curl https://api.qiwi.com/partner/bill/v1/bills/893794793973 \
-X PUT \
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjIwNDIsImFwaV91c2VyX2lkIjo1NjYwMzk3Miwic2VjcmV0IjoiQjIwODlDNkI5Q0NDNTdCNDQzNGHJK43JFJDK595FJFJMjlCRkFFRDM5OE***********************'
-d '{
"amount": {
"currency": "RUB",
"value": 100.00
},
"comment": "Text comment",
"expirationDateTime": "2018-04-13T14:30:00+03:00",
"customer": {},
"customFields": {}
}
<?php
$billId = '893794793973';
$fields = [
'amount' => 1.00,
'currency' => 'RUB',
'comment' => 'test',
'expirationDateTime' => '2018-03-02T08:44:07',
'email' => 'example@mail.org',
'account' => 'client4563'
];
/** @var \Qiwi\Api\BillPayments $billPayments */
$response = $billPayments->createBill($billId, $fields);
print_r($response);
?>
CreateBillInfo billInfo = new CreateBillInfo(
UUID.randomUUID().toString(),
new MoneyAmount(
BigDecimal.valueOf(199.90),
Currency.getInstance("RUB")
),
"comment",
ZonedDateTime.now().plusDays(45),
new Customer(
"example@mail.org",
UUID.randomUUID().toString(),
"79123456789"
),
""
);
BillResponse response = client.createBill(billInfo);
var billInfo = new CreateBillInfo
{
BillId = Guid.NewGuid().ToString(),
Amount = new MoneyAmount
{
ValueDecimal = 199.9m,
CurrencyEnum = CurrencyEnum.Rub
},
Comment = "comment",
ExpirationDateTime = DateTime.Now.AddDays(45),
Customer = new Customer
{
Email = "example@mail.org",
Account = Guid.NewGuid().ToString(),
Phone = "79123456789"
},
};
var response = client.createBill(billInfo);
Parameter | Description | Type | Required |
---|---|---|---|
billId | Unique invoice identifier in merchant's system | String(200) | + |
amount.currency | invoice amount rounded down to two decimals | (Alpha-3 ISO 4217 code) | + |
amount.value | Amount of the invoice rounded down to two decimals | Number(6.2) | + |
phone | Phone number of the client to which the invoice is issuing (international format) | string | - |
E-mail of the client where the invoice payment link will be sent | string | - | |
account | Client identifier in merchant's system | string | - |
comment | Invoice commentary | String(255) | - |
customFields[] | Additional invoice data | String(255) | - |
expirationDateTime | invoice due date. Time should be specified with time zone. | stringYYYY-MM-DDThhmm+\-hh:mm |
+ |
Response ←
Successful response body example
{
"siteId": "23044",
"billId": "893794793973",
"amount": {
"value": 100,
"currency": "RUB"
},
"status": {
"value": "WAITING",
"changedDateTime": "2018-03-05T11:27:41+03:00"
},
"comment": "Text comment",
"creationDateTime": "2018-03-05T11:27:41",
"expirationDateTime": "2018-04-13T14:30:00",
"payUrl": "https://oplata.qiwi.com/form/?invoice_uid=d875277b-6f0f-445d-8a83-f62c7c07be77"
}
Error response body
{
"serviceName": "invoicing-api",
"errorCode": "auth.unauthorized",
"description": "Неверные аутентификационные данные",
"userMessage": "",
"datetime": "2018-04-09T18:31:42+03:00",
"traceId" : "48485a395dfsdf34v124"
}
HEADERS
- Content-Type: application/json
Parameter | Type | Description |
---|---|---|
billId | String | Unique invoice identifier in the merchant's system |
siteId | String | Merchant's site identifier in QIWI Kassa |
amount.value | String | The invoice amount. The number is rounded down to two decimals |
amount.currency | String | Currency identifier of the invoice (Alpha-3 ISO 4217 code) |
status.value | String | String representation of the status |
status.changedDateTime | String | Status refresh date. Date format:YYYY-MM-DDThh:mm:ss±hh |
customer | Object | Customer data of the invoice subject |
customer.phone | String | The customer’s phone (if specified in the invoice) |
customer.email | String | The customer's e-mail (if specified in the invoice) |
customer.account | String | The customer's identifier in the merchant's system (if specified in the invoice) |
customFields | Object | Additional invoice data provided by the merchant |
comment | String | Comment to the invoice |
creationDateTime | String | System date of the invoice creation. Date format:YYYY-MM-DDThh:mm:ss±hh |
payUrl | String | Pay form link |
expirationDateTime | String | Expiration date of the pay form link (invoice payment's due date). Date format:YYYY-MM-DDThh:mm:ss±hh |
2. Invoice Payment Notifications
Request ← POST
Notification example
POST /qiwi-notify.php HTTP/1.1
Accept: application/json
Content-type: application/json
X-Api-Signature-SHA256: J4WNfNZd***V5mv2w=
Host: example.com
{ "bill":
{
"siteId":"23044",
"billId":"1519892138404fhr7i272a2",
"amount":{
"value":"100",
"currency":"RUB"
},
"status":{
"value":"PAID",
"datetime":"2018-03-01T11:16:12"
},
"customer":{},
"customFields":{},
"creationDateTime":"2018-03-01T11:15:39",
"expirationDateTime":"2018-04-01T11:15:39"
},
"version":"1"
}
Notification is a POST-request (callback). The request's body contains JSON-serialized invoice data encoded by UTF-8.
Notifications handler server URL is specified in kassa.qiwi.com in Protocol settings section.
HEADERS
- X-Api-Signature-SHA256: ***
- Accept: application/json
- Content-type: application/json
Authorization on Merchant's Server
Upon receiving inbound notification you need to verify it by digital signature from notification HTTP header X-Api-Signature-SHA256
. Signature is verified with HMAC algorithm integrity check with SHA256-hash function.
Signature verification algorithm is as follows:
-
Prepare a string of the following notification's parameters separated by
|
:invoice_parameters = {amount.currency}|{amount.value}|{billId}|{siteId}|{status.value}
where
{*}
is the value of the notification parameter. All values should be treated as strings. -
Apply HMAC-SHA256 function:
hash = HMAС(SHA256, invoice_parameters, secret_key)
where:
secret_key
– function key;invoice_parameters
– string from step 1.
-
Compare
X-Api-Signature-SHA256
header's value with the result of step 2.
const validSignatureFromNotificationServer =
'07e0ebb10916d97760c196034105d010607a6c6b7d72bfa1c3451448ac484a3b';
const notificationData = {
bill: {
siteId: 'test',
billId: 'test_bill',
amount: { value: 1, currency: 'RUB' },
status: { value: 'PAID', datetime: '2018-03-01T11:16:12+03' },
customer: {},
customFields: {},
creationDateTime: '2018-03-01T11:15:39+03',
expirationDateTime: '2018-04-15T11:15:39+03'
},
version: '1'
};
const merchantSecret = 'test-merchant-secret-for-signature-check';
qiwiApi.checkNotificationSignature(
validSignatureFromNotificationServer, notificationData, merchantSecret
); // true
<?php
$validSignatureFromNotificationServer = '07e0ebb10916d97760c196034105d010607a6c6b7d72bfa1c3451448ac484a3b';
$notificationData = [
'bill' => [
'siteId' => 'test',
'billId' => 'test_bill',
'amount' => ['value' => 1, 'currency' => 'RUB'],
'status' => ['value' => 'PAID']
],
'version' => '3'
];
$merchantSecret = 'test-merchant-secret-for-signature-check';
/** @var \Qiwi\Api\BillPayments $billPayments */
$billPayments->checkNotificationSignature(
$validSignatureFromNotificationServer, $notificationData, $merchantSecret
); // true
?>
String merchantSecret = "test-merchant-secret-for-signature-check";
Notification notification = new Notification(
new Bill(
"test",
"test_bill",
new MoneyAmount(
BigDecimal.ONE,
Currency.getInstance("RUB")
),
BillStatus.PAID
),
"3"
);
String validSignature = "07e0ebb10916d97760c196034105d010607a6c6b7d72bfa1c3451448ac484a3b";
BillPaymentsUtils.checkNotificationSignature(validSignature, notification, merchantSecret); //true
String and key of the signature are encoded in UTF-8.
Parameters
Invoice parameters are in the POST-request's body.
Parameter | Description | Type |
---|---|---|
bill | Invoice data | Object |
bill.billId | Invoice identifier in the merchant's system | String(200) |
bill.siteId | Merchant's site identifier in QIWI Kassa | String |
bill.amount | The invoice amount data | Object |
amount.value | The invoice amount. The number is rounded down to two decimals | Number(6.2) |
amount.currency | Currency identifier of the invoice (Alpha-3 ISO 4217 code) | String(3) |
bill.status | Invoice status data | Object |
status.value | Current invoice status | String |
status.changedDateTime | Status refresh date. Date format:YYYY-MM-DDThh:mm:ssZ |
String |
bill.customFields | Additional invoice data provided by the merchant | Object |
bill.customer | Customer data of the invoice subject (if specified in the invoice) | Object |
customer.phone | The customer’s phone (if specified in the invoice) | String |
customer.email | The customer's e-mail (if specified in the invoice) | String |
customer.account | The customer's identifier in the merchant's system (if specified in the invoice) | String |
bill.comment | Comment to the invoice | String(255) |
bill.creationDateTime | System date of the invoice creation. Date format:YYYY-MM-DDThh:mm:ssZ |
String |
bill.payUrl | Pay form link | String |
bill.expirationDateTime | Expiration date of the pay form link (invoice payment's due date). Date format:YYYY-MM-DDThh:mm:ssZ |
String |
version | Notification service version | String |
Response →
HTTP/1.1 200 OK
Content-Type: application/json
{
"error":"0"
}
HEADERS
- Content-type: application/json
After receiving inbound notification request, you should verify its signature and returns the JSON-response. The processing result code should be returned in response.
3. Checking the Invoice Status
Use this method to get current invoice payment status. We recommend using it after receiving the payment notification.
Request → GET
const billId = '893794793973';
qiwiApi.getBillInfo(billId).then( data => {
//do smth ith data
});
curl https://api.qiwi.com/partner/bill/v1/bills/893794793973 \
-X GET \
-H 'Accept: application/json' \
-H 'Authorization: Bearer eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjIwNDIsImFwaV91c2VyX2lkIjo1NjYwMzk3Miwic2VjcmV0IjoiQjIwODlDNkI5Q0NDNTdCNDQzNGHJK43JFJDK595FJFJMjlCRkFFRDM5OE***********************'
<?php
$billId = '893794793973';
/** @var \Qiwi\Api\BillPayments $billPayments */
$response = $billPayments->getBillInfo($billId);
print_r($response);
?>
String billId = "fcb40a23-6733-4cf3-bacf-8e425fd1fc71";
BillResponse response = client.getBillInfo(billId);
var billId = "fcb40a23-6733-4cf3-bacf-8e425fd1fc71";
var response = client.getBillInfo(billId);
URL https://api.qiwi.com/partner/bill/v1/bills/{billid}
- billId - unique invoice identifier generated by the merchant.
HEADERS
- Authorization: Bearer SECRET_KEY
- Accept: application/json
Response ←
Successful response body example
{
"siteId": "23044",
"billId": "893794793973",
"amount": {
"value": 2.42,
"currency": "RUB"
},
"status": {
"value": "WAITING",
"changedDateTime": "2018-02-28T11:43:23.386+03:00"
},
"customer": {
"email": "test@qiwi.com",
"phone": "79191234567",
"account": "user_account"
},
"customFields": {
"city": "Moscow"
},
"comment": "Text comment",
"creationDateTime": "2018-02-28T11:43:23.612+03:00",
"expirationDateTime": "2018-04-14T11:43:23+03:00",
"payUrl": "https://oplata.qiwi.com/form/?invoice_uid=6848dd49-e260-4343-b258-62199cffe8c1"
}
Error response body example
{
"serviceName": "invoicing",
"errorCode": "auth.unauthorized",
"description": "Неверные аутентификационные данные",
"userMessage": "",
"datetime": "2018-04-09T18:31:42+03:00",
"traceId" : ""
}
HEADERS
- Content-Type: application/json
Parameter | Type | Description |
---|---|---|
billId | String | Unique invoice identifier in the merchant's system |
siteId | String | Merchant's site identifier in QIWI Kassa |
amount | Object | The invoice amount data |
amount.value | Number | The invoice amount. The number is rounded down to two decimals |
amount.currency | String | Currency identifier of the invoice (Alpha-3 ISO 4217 code) |
status | Object | Invoice status data |
status.value | String | Current invoice status |
status.changedDateTime | String | Status refresh date |
customFields | Object | Additional invoice data provided by the merchant |
customer | Object | Customer data of the invoice subject |
customer.phone | String | The customer’s phone (if specified in the invoice) |
customer.email | String | The customer's e-mail (if specified in the invoice) |
customer.account | String | The customer's identifier in the merchant's system (if specified in the invoice) |
comment | String | Comment to the invoice |
creationDateTime | String | System date of the invoice creation. Date format:YYYY-MM-DDThh:mm:ss |
payUrl | String | Pay form URL |
expirationDateTime | String | Expiration date of the pay form link (invoice payment's due date). Date format:YYYY-MM-DDThh:mm:ss |
4. Cancelling the Invoice
Use this method to cancel unpaid invoice.
Request → POST
const bill_id = '893794793973';
qiwiApi.cancelBill(billId).then( data => {
//do smth with data
});
curl https://api.qiwi.com/partner/bill/v1/bills/893794793973/reject \
-X POST \
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjIwNDIsImFwaV91c2VyX2lkIjo1NjYwMzk3Miwic2VjcmV0IjoiQjIwODlDNkI5Q0NDNTdCNDQzNGHJK43JFJDK595FJFJMjlCRkFFRDM5OE***********************'
<?php
$billId = '893794793973';
/** @var \Qiwi\Api\BillPayments $billPayments */
$response = $billPayments->cancelBill($billId);
print_r($response);
?>
String billId = "fcb40a23-6733-4cf3-bacf-8e425fd1fc71";
BillResponse response = client.cancelBill(billId);
var billId = "fcb40a23-6733-4cf3-bacf-8e425fd1fc71";
var response = client.cancelBill(billId);
URL https://api.qiwi.com/partner/bill/v1/bills/{billId}/reject
-
Parameters:
- billId - unique invoice identifier generated by the merchant.
HEADERS
- Authorization: Bearer SECRET_KEY
- Accept: application/json
Response ←
Successful response body example
{
"siteId": "23044",
"billId": "893794793973",
"amount": {
"value": 2.42,
"currency": "RUB"
},
"status": {
"value": "REJECTED",
"datetime": "2018-02-28T11:43:23"
},
"customer": {
"email": "test@qiwi.com",
"phone": "79191234567",
"account": "user_account"
},
"customFields": {
"city": "Moscow"
},
"comment": "Text comment",
"creationDateTime": "2018-02-28T11:43:23",
"expirationDateTime": "2018-04-14T11:43:23",
"payUrl": "https://oplata.qiwi.com/form/?invoice_uid=6848dd49-e260-4343-b258-62199cffe8c1"
}
Error response body example
{
"serviceName": "invoicing",
"errorCode": "auth.unauthorized",
"description": "Неверные аутентификационные данные",
"userMessage": "",
"datetime": "2018-04-09T18:31:42+03:00",
"traceId" : ""
}
HEADERS
- Content-Type: application/json
Parameter | Type | Description |
---|---|---|
billId | String | Unique invoice identifier in the merchant's system |
siteId | String | Merchant's site identifier in QIWI Kassa |
amount | Object | The invoice amount data |
amount.value | Number | The invoice amount. The number is rounded down to two decimals |
amount.currency | String | Currency identifier of the invoice (Alpha-3 ISO 4217 code) |
status | Object | Invoice status data |
status.value | String | Current invoice status |
status.changedDateTime | String | Status refresh date |
customFields | Object | Additional invoice data provided by the merchant |
customer | Object | Customer data of the invoice subject |
customer.phone | String | The customer’s phone (if specified in the invoice) |
customer.email | String | The customer's e-mail (if specified in the invoice) |
customer.account | String | The customer's identifier in the merchant's system (if specified in the invoice) |
comment | String | Comment to the invoice |
creationDateTime | String | System date of the invoice creation. Date format:YYYY-MM-DDThh:mm:ss |
payUrl | String | Pay form URL |
expirationDateTime | String | Expiration date of the pay form link (invoice payment's due date). Date format:YYYY-MM-DDThh:mm:ss |
5. Refund
Method allows you to make a refund for the paid invoice.
Request → PUT
const billId = '893794793973';
const refundId = '899343443';
const amount = 12;
const currency = 'RUB'
qiwiApi.refund(billId, refundId, amount, currency).then( data => {
//do smth with data
});
curl https://api.qiwi.com/partner/bill/v1/bills/893794793973/refunds/899343443 \
-X PUT \
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjIwNDIsImFwaV91c2VyX2lkIjo1NjYwMzk3Miwic2VjcmV0IjoiQjIwODlDNkI5Q0NDNTdCNDQzNGHJK43JFJDK595FJFJMjlCRkFFRDM5OE***********************'
-d '{
"amount": {
"currency": "RUB",
"value": 1
}
}'
<?php
$billId = '893794793973';
$refundId = '899343443';
$amount = 12;
$currency = 'RUB';
/** @var \Qiwi\Api\BillPayments $billPayments */
$response = $billPayments->refund($billId, $refundId, $amount, $currency);
print_r($response);
?>
String billId = "fcb40a23-6733-4cf3-bacf-8e425fd1fc71";
String refundId = UUID.randomUUID().toString();
MoneyAmount amount = new MoneyAmount(
BigDecimal.valueOf(104.90),
Currency.getInstance("RUB")
);
RefundResponse refundResponse = client.refundBill(paidBillId, refundId, amount);
var billId = "fcb40a23-6733-4cf3-bacf-8e425fd1fc71";
var refundId = Guid.NewGuid().ToString();
var amount = new MoneyAmount
{
ValueDecimal = 104.9m,
CurrencyEnum = CurrencyEnum.Rub
};
var refundResponse = client.refundBill(paidBillId, refundId, amount);
URL https://api.qiwi.com/partner/bill/v1/bills/{billId}/refunds/{refundId}
-
Parameters:
- billId - unique invoice identifier generated by the merchant.
- refundId - unique refund identifier generated by the merchant.
- in JSON body:
- amount.value - refund amount.
- amount.currency - refund currency.
HEADERS
- Authorization: Bearer SECRET_KEY
- Accept: application/json
- Content-Type: application/json
Response ←
Successful response body example
{
"amount": {
"value": 50.50,
"currency": "RUB"
},
"datetime": "2018-03-01T16:06:57+03",
"refundId": "1",
"status": "PARTIAL"
}
Error response body example
{
"serviceName": "invoicing",
"errorCode": "refund.incorrect.amount",
"description": "Неверная сумма возврата",
"userMessage": "Неверная сумма возврата",
"datetime": "2005-08-09T18:31:42+03:00",
"traceId" : ""
}
HEADERS
- Content-Type: application/json
Parameter | Type | Description |
---|---|---|
datetime | String | When response with error: request processing system date |
refundId | String | Unique refund identifier given by the merchant |
amount.value | Number | The invoice amount. The number is rounded down to two decimals |
amount.currency | String | Currency identifier of the invoice (Alpha-3 ISO 4217 code) |
status | String | Refund status |
datetime | String | System date of refund processing. Date format:YYYY-MM-DDThh:mm:ssZ |
6. Refund Status
Method returns current status of the refund .
Request → GET
const billId = '893794793973';
const refundId = '899343443';
qiwiApi.getRefundInfo(billId, refundId).then( data => {
//do smth with data
});
curl https://api.qiwi.com/partner/bill/v1/bills/893794793973/refund/899343443 \
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjIwNDIsImFwaV91c2VyX2lkIjo1NjYwMzk3Miwic2VjcmV0IjoiQjIwODlDNkI5Q0NDNTdCNDQzNGHJK43JFJDK595FJFJMjlCRkFFRDM5OE***********************'
<?php
$billId = '893794793973';
$refundId = '899343443';
/** @var \Qiwi\Api\BillPayments $billPayments */
$response = $billPayments->getRefundInfo($billId, $refundId);
print_r($response);
?>
String billId = "fcb40a23-6733-4cf3-bacf-8e425fd1fc71";
String refundId = '3444e8ca-cf68-4dbd-92ee-f68c4bf8f29b';
RefundResponse response = client.getRefundInfo(paidBillId, refundId);
var billId = "fcb40a23-6733-4cf3-bacf-8e425fd1fc71";
var refundId = "3444e8ca-cf68-4dbd-92ee-f68c4bf8f29b";
var response = client.getRefundInfo(paidBillId, refundId);
URL https://api.qiwi.com/partner/bill/v1/bills/{billId}/refunds/{refundId}
-
Parameters:
- billId - unique invoice identifier generated by the merchant.
- refundId - unique refund identifier generated by the merchant.
HEADERS
- Authorization: Bearer SECRET_KEY
- Accept: application/json
Response ←
Successful response body example
{
"amount": {
"value": 50.50,
"currency": "RUB"
},
"datetime": "2018-03-01T16:06:57+03",
"refundId": "1",
"status": "PARTIAL"
}
Error response body example
{
"serviceName": "invoicing",
"errorCode": "refund.incorrect.amount",
"description": "Неверная сумма возврата",
"userMessage": "Неверная сумма возврата",
"datetime": "2005-08-09T18:31:42+03:00",
"traceId" : ""
}
HEADERS
- Content-Type: application/json
Parameter | Type | Description |
---|---|---|
datetime | String | When response with error: request processing system date |
refundId | String | Unique refund identifier given by the merchant |
amount.value | Number | The invoice amount. The number is rounded down to two decimals |
amount.currency | String | Currency identifier of the invoice (Alpha-3 ISO 4217 code) |
status | String | Refund status |
datetime | String | System date of refund processing. Date format:YYYY-MM-DDThh:mm:ssZ |
Invoice Payment Statuses
Status | Description | Final |
---|---|---|
WAITING | Invoice issued awaiting for payment | - |
PAID | Invoice paid | + |
REJECTED | Invoice rejected by customer | + |
EXPIRED | Invoice expired. Invoice not paid | + |
Refund Statuses
Status | Description | Final |
---|---|---|
PARTIAL | Partial refund of the invoice amount | - |
FULL | Full refund of the invoice amount | + |
Additional features
Invoice Issue on Payment Form
It is the simplest way of integration. On opening Payment Form, client receives an invoice at the same time. The invoice data sends in URL explicitly. Client gets a Payment Form web page with multiple payment means. When using this method, one cannot be sure that all invoices are issued by the merchant. API invoice creation mitigates this risk.
REDIRECT →
URL https://oplata.qiwi.com/create
const QiwiBillPaymentsAPI = require('bill-payments-node-js-sdk');
const SECRET_KEY = 'eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjUyNjgxMiwiYXBpX3VzZXJfaWQiOjcxNjI2MTk3LCJzZWNyZXQiOiJmZjBiZmJiM2UxYzc0MjY3YjIyZDIzOGYzMDBkNDhlYjhiNTnONPININONPN090MTg5Z**********************';
const qiwiApi = new QiwiBillPaymentsAPI(SECRET_KEY);
--header "Authorization: Bearer MjMyNDQxMjM6NDUzRmRnZDQ0M*******"
<?php
$publicKey = '2tbp1WQvsgQeziGY9vTLe9vDZNg7tmCymb4Lh6STQokqKrpCC6qrUUKEDZAJ7mvFnzr1yTebUiQaBLDnebLMMxL8nc6FF5zf******';
$params = [
'publicKey' => $publicKey,
'amount' => 200,
'billId' => '893794793973'
];
/** @var \Qiwi\Api\BillPayments $billPayments */
$link = $billPayments->createPaymentForm($params);
echo $link;
?>
String publicKey = "2tbp1WQvsgQeziGY9vTLe9vDZNg7tmCymb4Lh6STQokqKrpCC6qrUUKEDZAJ7mvFnzr1yTebUiQaBLDnebLMMxL8nc6FF5zfmGQnypdXCbQJqHEJW5RJmKfj8nvgc";
MoneyAmount amount = new MoneyAmount(
BigDecimal.valueOf(499.90),
Currency.getInstance("RUB")
);
String billId = UUID.randomUUID().toString();
String paymentUrl = client.createPaymentForm(new PaymentInfo(key, amount, billId, ""));
var publicKey = "2tbp1WQvsgQeziGY9vTLe9vDZNg7tmCymb4Lh6STQokqKrpCC6qrUUKEDZAJ7mvFnzr1yTebUiQaBLDnebLMMxL8nc6FF5zfmGQnypdXCbQJqHEJW5RJmKfj8nvgc";
var amount = new MoneyAmount
{
ValueDecimal = 499.9m,
CurrencyEnum = CurrencyEnum.Rub
};
var billId = Guid.NewGuid().ToString();
var paymentUrl = client.createPaymentForm(new PaymentInfo(key, amount, billId, ""));
const publicKey = 'Fnzr1yTebUiQaBLDnebLMMxL8nc6FF5zfmGQnypc*******';
const params = {
publicKey,
amount: 42.24,
billId: '893794793973',
email: 'm@ya.ru'
};
const link = qiwiApi.createPaymentForm(params);
curl https://oplata.qiwi.com/create?publicKey=Fnzr1yTebUiQaBLDnebLMMxL8nc6FF5zfmGQnypc*******&amount=100&billId=893794793973&email=m@ya.ru
Parameters
Invoice data are put in Payment Form URL.
Parameter | Description | Type | Required |
---|---|---|---|
publicKey | Merchant public key received in QIWI Kassa | String | + |
billId | Unique invoice identifier given by the merchant | URL-encoded, String(200) | - |
amount | Amount of the invoice rounded down on two decimals | Number(6.2) | - |
phone | Phone number of the client to which the invoice is issuing (international format) | URL-encoded string | - |
E-mail of the client where the invoice payment link will be sent | URL-encoded string | - | |
account | Client identifier | URL-encoded string | - |
comment | Invoice commentary | URL-encoded, String(255) | - |
customFields[] | Additional invoice data | URL-encoded, String(255) | - |
lifetime | Expiration date of the pay form link (invoice payment due date). If the invoice is not paid after that date, the invoice assigns EXPIRED final status and it becomes void.Important! Invoice will be automatically expired when 45 days is passed after the invoicing date |
URL-encoded stringYYYY-MM-DDThhmm |
- |
Personalization
Personalization allows you to create a payment form with your style, customizable logo, background and color of the buttons.
You can create styles in your account on kassa.qiwi.com. It is possible to create several styles.
When setting up, you create a code linked to the style (for example, codeStyle
). To use style on the Payment Form, you must pass the variable: "themeCode": "codeStyle"
with respective code of the style in the customFields
parameter of the invoice request or opening Payment Form URL.
Invoice Issue on Payment Form
curl https://oplata.qiwi.com/create?publicKey=Fnzr1yTebUiQaBLDnebLMMxL8nc6FF5zfmGQnypc*******&amount=100&billId=893794793973&customFields%5BthemeCode%5D=codeStyle
Invoice Issue by API
curl https://api.qiwi.com/partner/bill/v1/bills/893794793973 \
-X PUT \
-H 'Accept: application/json' \
-H 'Content-Type: application/json' \
-H 'Authorization: Bearer eyJ2ZXJzaW9uIjoicmVzdF92MyIsImRhdGEiOnsibWVyY2hhbnRfaWQiOjIwNDIsImFwaV91c2VyX2lkIjo1NjYwMzk3Miwic2VjcmV0IjoiQjIwODlDNkI5Q0NDNTdCNDQzNGHJK43JFJDK595FJFJMjlCRkFFRDM5OE***********************' \
-d '{ \
"amount": { \
"currency": "RUB", \
"value": 100.00 \
}, \
"comment": "Text comment", \
"expirationDateTime": "2018-04-13T14:30:00+03:00", \
"customer": {}, \
"customFields": {"themeCode":"codeStyle"} \
}'
Checkout Popup
Installation:
The library has two methods: create a new invoice and open an existing one.
Create new invoice
Call function QiwiCheckout.createInvoice
Parameter | Description | Type | Required |
---|---|---|---|
publicKey | Merchant public key received in QIWI Kassa | String | + |
amount | Amount of the invoice rounded down on two decimals | Number(6.2) | + |
phone | Phone number of the client to which the invoice is issuing (international format) | String | - |
E-mail of the client where the invoice payment link will be sent | String | - | |
account | Client identifier in merchant’s system | String | - |
comment | Invoice commentary | String(255) | - |
customFields | Additional invoice data | Object | - |
lifetime | Expiration date of the pay form link (invoice payment’s due date). If the invoice is not paid after that date, the invoice assigns EXPIRED final status and it becomes void.Important! Invoice will be automatically expired when 45 days is passed after the invoicing date |
URL-encoded string YYYY-MM-DDThhmm |
- |
Create new invoice
params = {
publicKey: '5nAq6abtyCz4tcDj89e5w7Y5i524LAFmzrsN6bQTQ3c******',
amount: 1.23,
phone: '79123456789',
email: 'test@test.com',
account: 'acc789',
comment: 'Оплата',
customFields: {
data: 'data'
},
lifetime: '2019-04-04T1540'
}
QiwiCheckout.createInvoice(params)
.then(data => {
// ...
})
.catch(error => {
// ...
})
Open an existing invoice
Call function QiwiCheckout.openInvoice
Parameter | Description | Type | Required |
---|---|---|---|
payUrl | Pay form URL | String | + |
Open an existing one
params = {
payUrl: 'https://oplata.qiwi.com/form?invoiceUid=06df838c-0f86-4be3-aced-a950c244b5b1'
}
QiwiCheckout.openInvoice(params)
.then(data => {
// ...
})
.catch(error => {
// ...
})
Invoice opening options
Invoice URL example
curl https://oplata.qiwi.com/form?invoiceUid=606a5f75-4f8e-4ce2-b400-967179502275&allowedPaySources=card
You can add parameters to URL from payUrl
field of the response to invoice request.
Parameter | Description | Type |
---|---|---|
paySource | Pre-selected payment method for the client on Payment Form. Possible values: qw - QIWI Walletcard - card payment mobile - mobile account payment sovest - Sovest card payment When specified method is inaccessible, the page automatically selects recommended method for the user. |
String |
allowedPaySources | Allow only these payment methods for the client on Payment Form. Possible values: qw - QIWI Walletcard - card payment mobile - mobile account payment sovest - Sovest card payment |
comma separated string |
lifetime | Expiration date of the pay form link (invoice payment’s due date). If the invoice is not paid after that date, the invoice assigns EXPIRED final status and it becomes void. Important! Invoice will be automatically expired when 45 days is passed after the invoicing date | StringYYYY-MM-DDThhmm |
SDK and CMS
SDK and Libraries
- NODE JS SDK - Node JS package of ready-to-use solutions for server2server integration development.
- PHP SDK - PHP package of ready-to-use solutions for server2server integration development.
- Java SDK - Java package of ready-to-use solutions for server2server integration development.
- .Net SDK - C# .net package of ready-to-use solutions for server2server integration development.
CMS Solutions
- Wordpress - plugin for Woocommerce for work with orders
- Online Leyka - Wordpress plagin for charity
- 1С-Bitrix - plugin for work with orders
- Opencart - plugin for work with orders
- PrestaShop - plugin for work with orders
Design recommendation
Design guideline
This guideline helps to reduce the time it takes customers to go from checkout to payment form.
-
If API QIWI Kassa is the one of payments methods on your page, we recommend to show all available payment methods' icons:
You can use 'QIWI Кассa' without logo (payment methods' icons are required):
-
If API QIWI Kassa is the only one method on your checkout, 'QIWI Кассa' or QIWI logo is not required. Show payment methods' icons under a payment button: