Return items of a sale receipt
This tutorial demonstrates how to handle item returns.
You''ll learn how to
- Return items of a sale receipt issued by the same Point of Sale you are operating from.
- Return items of a sale receipt issued by a different Point of Sale.
- Return items of a sale receipt that hasn't been issued by a Point of Sale.
Prerequisites
Receipts can be issued only by a merchant or a cashier with a valid certificate (PEM file).
Case 1: Return items of a sale receipt issued by the same Point of Sale
Since our goal is to return items of a sale receipt, we will issue one from a cash register associated to the Point of Sale E001-000001 and use it as reference. In particular we'll make a POST HTTP request to https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipt with body
{
"electronic_payment_amount": "244",
"items":
[
{
"type": "goods",
"quantity": "1",
"description": "Product A",
"unit_price": "122",
"vat_rate_code": "22"
},
{
"type": "goods",
"quantity": "1",
"description": "Product B",
"unit_price": "122",
"vat_rate_code": "22"
}
]
}And obtain a 201 response with body
{
"uuid": "18a681da-a868-47ba-a931-2f702474c3d1",
"type": "sale",
"total_amount": "244",
"document_number": "0001-0001",
"document_datetime": "2025-09-01T10:00:00",
"parent_receipt_uuid": null
}In this case, the required fields to issue the return receipts are minimal, because the Point of Sale E001-000001 has also issued the sale receipt, therefore it can automatically retrieve most of the needed infomation.
Before issuing the return receipt, you can query the system to retrieve the returnable amount for each item of the sale receipt:
import requests
CERT_PATH = '/var/certs/pos/E001-000001/cashregister.pem'
KEY_PATH = '/var/certs/pos/E001-000001/cashregister.pem'
response = requests.get(
'https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/18a681da-a868-47ba-a931-2f702474c3d1/returnable-items',
cert=(CERT_PATH, KEY_PATH)
)const fs = require('fs');
const https = require('https');
const CERT = fs.readFileSync('/var/certs/pos/E001-000001/cashregister.pem')
const KEY = fs.readFileSync('/var/certs/pos/E001-000001/cashregister.pem')
const req = https.request(
{
hostname: 'ereceipts-it-sandbox.acubeapi.com',
headers: {
"Content-Type": "application/json"
},
port: 444,
path: '/mf1/receipts/18a681da-a868-47ba-a931-2f702474c3d1/returnable-items',
method: 'GET',
cert: CERT,
key: KEY
}
);
req.end();curl -X GET https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/18a681da-a868-47ba-a931-2f702474c3d1/returnable-items \
-H 'Content-Type: application/json' \
--cert /var/certs/pos/E001-000001/cashregister.pem \
--key /var/certs/pos/E001-000001/cashregister.pem$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/18a681da-a868-47ba-a931-2f702474c3d1/returnable-items');
curl_setopt($ch, CURLOPT_HTTPHEADER, ['Content-Type:application/json']);
curl_setopt($ch, CURLOPT_SSLCERT, '/var/certs/pos/E001-000001/cashregister.pem');
curl_setopt($ch, CURLOPT_SSLKEY, '/var/certs/pos/E001-000001/cashregister.pem');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
curl_close($ch);You will obtain a 200 status code and the following response body:
[
{
"id": 1,
"type": "goods",
"quantity": "1",
"returned_quantity": "0",
"description": "Product A",
"unit_price": "122",
"vat_rate_code": "22"
},
{
"id": 2,
"type": "goods",
"quantity": "1",
"returned_quantity": "0",
"description": "Product B",
"unit_price": "122",
"vat_rate_code": "22"
}
]Now that you have access to each item's ID and returnable quantity, you can successfully return (for example) one quantity of the item Product B:
import requests
CERT_PATH = '/var/certs/pos/E001-000001/cashregister.pem'
KEY_PATH = '/var/certs/pos/E001-000001/cashregister.pem'
response = requests.post(
'https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/return',
cert=(CERT_PATH, KEY_PATH),
json={
"document_number": "0001-0001",
"items": [
{
"id": 2,
"quantity": "1"
}
]
}
)const fs = require('fs');
const https = require('https');
const CERT = fs.readFileSync('/var/certs/pos/E001-000001/cashregister.pem')
const KEY = fs.readFileSync('/var/certs/pos/E001-000001/cashregister.pem')
const req = https.request(
{
hostname: 'ereceipts-it-sandbox.acubeapi.com',
headers: {
"Content-Type": "application/json"
},
port: 444,
path: '/mf1/receipts/return',
method: 'POST',
cert: CERT,
key: KEY
},
res => {
let body = '';
res.on('data', function(data) {
body += data;
});
res.on('end', function() {
console.log(body);
})
}
);
req.write(JSON.stringify( {
"document_number": "0001-0001",
"items": [
{
"id": 2,
"quantity": "1"
}
]
}));
req.end();curl -X POST https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/return \
-H 'Content-Type: application/json' \
-d '{"document_number":"0001-0001","items":[{"id": 1,"quantity":"1"}]}' \
--cert /var/certs/pos/E001-000002/cashregister.pem \
--key /var/certs/pos/E001-000002/cashregister.pem$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/return');
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode('{
"document_number": "0001-0001",
"items": [
{
"id": 2,
"quantity": "1"
}
]
}'));
curl_setopt($ch, CURLOPT_HTTPHEADER, ['Content-Type:application/json']);
curl_setopt($ch, CURLOPT_SSLCERT, '/var/certs/pos/E001-000001/cashregister.pem');
curl_setopt($ch, CURLOPT_SSLKEY, '/var/certs/pos/E001-000001/cashregister.pem');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
curl_close($ch);This will result in a 201 status code and the following response body:
{
"uuid": "25a34bea-3418-17ba-ac31-2f704474abb3",
"type": "return",
"total_amount": "122",
"document_number": "0001-0002",
"document_datetime": "2025-09-01T11:00:00",
"parent_receipt_uuid": "18a681da-a868-47ba-a931-2f702474c3d1"
}A subsequent GET request to https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/18a681da-a868-47ba-a931-2f702474c3d1/returnable-items will return:
[
{
"id": 1,
"type": "goods",
"quantity": "1",
"returned_quantity": "0",
"description": "Product A",
"unit_price": "122",
"vat_rate_code": "22"
},
{
"id": 2,
"type": "goods",
"quantity": "0",
"returned_quantity": "1",
"description": "Product B",
"unit_price": "122",
"vat_rate_code": "22"
}
]Case 2: Sale receipt issued by another Point of Sale
If the sale receipt has been issued by a different Point of Sale with respect to the one from which you are operating from, you should make a POST request to mf1/receipts/return-via-different-pos.
For example, if you want to return the sale receipt previously issued by the Point of Sale E001-000001 from the Point of Sale E001-000002, then you would make a POST request to https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/return-via-different-pos:
import requests
CERT_PATH = '/var/certs/pos/E001-000002/cashregister.pem'
KEY_PATH = '/var/certs/pos/E001-000002/cashregister.pem'
response = requests.post(
'https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/return-via-different-pos',
cert=(CERT_PATH, KEY_PATH),
json={
"pos_id": "E001-000001",
"items": [
{
"type": "goods",
"quantity": "1",
"description": "Product B",
"unit_price": "122",
"vat_rate_code": "22"
}
],
"document_number": "0001-0001",
"document_datetime": "2025-09-01T10:00:00",
}
)const fs = require('fs');
const https = require('https');
const CERT = fs.readFileSync('/var/certs/pos/E001-000002/cashregister.pem')
const KEY = fs.readFileSync('/var/certs/pos/E001-000002/cashregister.pem')
const req = https.request(
{
hostname: 'ereceipts-it-sandbox.acubeapi.com',
headers: {
"Content-Type": "application/json"
},
port: 444,
path: '/mf1/receipts/return-via-different-pos',
method: 'POST',
cert: CERT,
key: KEY
},
res => {
let body = '';
res.on('data', function(data) {
body += data;
});
res.on('end', function() {
console.log(body);
})
}
);
req.write(JSON.stringify( {
"pos_id": "E001-000001",
"items": [
{
"type": "goods",
"quantity": "1",
"description": "Product B",
"unit_price": "122",
"vat_rate_code": "22"
}
],
"document_number": "0001-0001",
"document_datetime": "2025-09-01T10:00:00",
}));
req.end();curl -X POST https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/return-via-different-pos \
-H 'Content-Type: application/json' \
-d '{"pos_id":"E001-000001","items":[{"type": "goods", "quantity":"1", "description": "Product B", "unit_price": "122", "vat_rate_code": "22"}], "document_number": "0001-0001", "document_datetime": "2025-09-01T10:00:00"}' \
--cert /var/certs/pos/E001-000002/cashregister.pem \
--key /var/certs/pos/E001-000002/cashregister.pem$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipts/return-via-different-pos');
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode('{
"pos_id": "E001-000001",
"items": [
{
"type": "goods",
"quantity": "1",
"description": "Product B",
"unit_price": "122",
"vat_rate_code": "22"
}
],
"document_number": "0001-0001",
"document_datetime": "2025-01-01T10:00:00",
}'));
curl_setopt($ch, CURLOPT_HTTPHEADER, ['Content-Type:application/json']);
curl_setopt($ch, CURLOPT_SSLCERT, '/var/certs/pos/E001-000002/cashregister.pem');
curl_setopt($ch, CURLOPT_SSLKEY, '/var/certs/pos/E001-000002/cashregister.pem');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
curl_close($ch);And obtain a 201 status code and the following response body:
{
"uuid": "62f25bea-2818-3ae2-ac26-1e562288bee1",
"type": "return",
"total_amount": "122",
"document_number": "0027-0120", // this value depends on how many receipts has been issued by E001-000002
"document_datetime": "2025-09-01T11:00:00",
"parent_receipt_uuid": null
}Note that in this case parent_receipt_uuid is null because the return receipt is weakly associated to the sale receipt issued by E001-000001.
Case 3: Sale receipt not issued by a Point of Sale
It might be that the sale receipt has not been issued by a Point of Sale, so it is not possible to specify a document_number.
In this case you should make a POST request to /mf1/receipts/return-with-proof:
import requests
CERT_PATH = '/var/certs/pos/E001-000001/cashregister.pem'
KEY_PATH = '/var/certs/pos/E001-000001/cashregister.pem'
response = requests.post(
'https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipt/return-with-proof',
cert=(CERT_PATH, KEY_PATH),
json= {
"proof": "POS",
"document_datetime": "2025-09-01T10:00:00",
"items":
[
{
"type": "goods",
"quantity": "1",
"description": "Product B",
"unit_price": "100",
"vat_rate_code": "22"
}
]
}
)const fs = require('fs');
const https = require('https');
const CERT = fs.readFileSync('/var/certs/pos/E001-000001/cashregister.pem')
const KEY = fs.readFileSync('/var/certs/pos/E001-000001/cashregister.pem')
const req = https.request(
{
hostname: 'ereceipts-it-sandbox.acubeapi.com',
headers: {
"Content-Type": "application/json"
},
port: 444,
path: '/mf1/receipt/return-with-proof',
method: 'POST',
cert: CERT,
key: KEY
},
res => {
let body = '';
res.on('data', function(data) {
body += data;
});
res.on('end', function() {
console.log(body);
})
}
);
req.write(JSON.stringify( {
"proof": "POS",
"document_datetime": "2025-09-01T10:00:00",
"items":
[
{
"type": "goods",
"quantity": "1",
"description": "Product B",
"unit_price": "100",
"vat_rate_code": "22"
}
]
}));
req.end();curl -X POST https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipt/return-with-proof \
-H 'Content-Type: application/json' \
-d '{"proof":"POS","document_datetime":"2025-09-01T10:00:00","items":[{"good_or_service":"B","quantity":"1","description":"Product B","unit_price":"100","vat_rate_code":"22"}]}' \
--cert /var/certs/pos/E001-000001/cashregister.pem \
--key /var/certs/pos/E001-000001/cashregister.pem$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'https://ereceipts-it-sandbox.acubeapi.com:444/mf1/receipt/return-with-proof');
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode('{
"proof": "POS",
"document_datetime": "2025-09-01T10:00:00",
"items":
[
{
"type": "goods",
"quantity": "1",
"description": "Product B",
"unit_price": "100",
"vat_rate_code": "22"
}
]
}'));
curl_setopt($ch, CURLOPT_HTTPHEADER, ['Content-Type:application/json']);
curl_setopt($ch, CURLOPT_SSLCERT, '/var/certs/pos/E001-000001/cashregister.pem');
curl_setopt($ch, CURLOPT_SSLKEY, '/var/certs/pos/E001-000001/cashregister.pem');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
curl_close($ch);info
This endpoint requires you to specify time and date of the sale receipt for which you are returning items.
info
the field proof can be set to one of "POS", "VR" (vuoti a rendere), or "ND" (non definito). "POS" in this case refers to a payment processing device, not the Point of Sale entity referred to in this documentation.