Skip to main content

Generate PDF receipt after the order has been placed

In this example, we place an order, read it back with full pricing data and assemble a printable receipt that can be rendered as a PDF on the client.

✅ Purpose of the scenario:

  • Place an order and read it back with Orders.getOrderByMarkerAndId()
  • Assemble a receipt from the order's products, totals and payment method
  • Render the receipt as a downloadable PDF on the client

✅ What you need:

  • A valid PROJECT_URL and APP_TOKEN for authentication with the OneEntry API.
  • Registered user
  • Configured order storage with marker "orders"

📌 Important:

  • PDF rendering is not part of the OneEntry SDK — use any client-side library (jsPDF is shown here). The SDK only provides the order data.
  • totalSum comes back as a string and currency is often empty — format with Number(totalSum).toFixed(2) and never hardcode a currency symbol.
  • These examples do not include error handling.
  • You can manage errors using a try-catch block or by employing a construction like await Promise.catch((error) => error).

📚 See in documentation:

📦 SDK reference:

Try it live

Run this method interactively in the JS SDK sandbox — connect your Project URL and App Token on first visit, then open:

Scenario

1. Import defineOneEntry from SDK and define PROJECT_URL and APP_TOKEN

Example:

import { defineOneEntry } from 'oneentry';

const PROJECT_URL = 'your-project-url';
const APP_TOKEN = 'your-app-token';

2. Creating an API client with defineOneEntry()

Example:

const { AuthProvider, Orders } = defineOneEntry(PROJECT_URL, {
token: APP_TOKEN,
});

3. User authorization with AuthProvider.auth()

Example:

const authData = [
{ marker: 'email_reg', value: 'your-email' },
{ marker: 'password_reg', value: 'your-password' },
];
const user = await AuthProvider.auth('email', { authData });
console.log(user);
Result:
{
"userIdentifier": "kvasssukr.net@gmail.com",
"authProviderIdentifier": "email",
"accessToken": "eyJhbGciOiJIUzI1NiIsInR...pZCI6MTYsImF1dGhQ"
"refreshToken": "1745494429101-...-2834edf8"
}

4. Place the order with Orders.createOrder()

Data:

{
"formIdentifier": "order",
"paymentAccountIdentifier": "cash",
"formData": {
"en_US": [
{
"type": "string",
"marker": "name",
"value": "Christina Thomas"
}
]
},
"products": [
{
"productId": 15,
"quantity": 1
}
]
}

Example:

const body = {
formIdentifier: 'order',
paymentAccountIdentifier: 'cash',
formData: [{ type: 'string', marker: 'name', value: 'Christina Thomas' }],
products: [{ productId: 15, quantity: 1 }],
};
const created = await Orders.createOrder('orders', body as any);

if ('statusCode' in created) {
throw new Error(created.message);
}
Result:
{
"id": 127,
"formIdentifier": "order",
"paymentAccountIdentifier": "cash",
"formData": [
{
"type": "string",
"marker": "name",
"value": "Christina Thomas"
}
],
"products": [
{
"productId": 15,
"quantity": 1
}
],
"currency": "USD",
"totalSum": 400,
"bonusApplied": 0,
"totalDue": 400,
"discountConfig": {
"orderDiscounts": [],
"productDiscounts": [],
"coupon": null,
"settings": {
"allowStacking": false,
"maxDiscountValue": null,
"allowGiftStacking": false,
"maxBonusPaymentPercent": null,
"minBonusAmount": null,
"minOrderAmountForBonus": null,
"giftRefundPolicy": "KEEP_GIFT"
},
"additionalDiscountsMarkers": [],
"totalRaw": 400,
"totalSumWithDiscount": 400,
"excludedGiftProductIds": [],
"bonus": {
"availableBalance": 0,
"maxBonusDiscount": 0,
"minBonusAmount": null,
"minOrderAmountForBonus": null,
"bonusApplied": 0
},
"bonusApplied": 0,
"totalDue": 400
},
"statusIdentifier": "upcoming",
"statusLocalizeInfos": {
"title": "Upcoming"
},
"createdDate": "2026-06-06T12:04:52.459Z"
}

5. Read the placed order back with Orders.getOrderByMarkerAndId()

Example:

// This returns the full order: products with titles/prices, totalSum, currency,
// payment method and status — everything the receipt needs.
const order = await Orders.getOrderByMarkerAndId('orders', created.id);

if ('statusCode' in order) {
throw new Error(order.message);
}
Result:
{
"id": 127,
"storageId": 1,
"createdDate": "2026-06-06T12:04:52.459Z",
"statusIdentifier": "upcoming",
"statusLocalizeInfos": {
"title": "Upcoming"
},
"formIdentifier": "order",
"formData": [
{
"type": "string",
"marker": "name",
"value": "Christina Thomas"
}
],
"attributeSetIdentifier": "order",
"paymentStrategy": "once",
"totalSum": "400",
"totalSumRaw": "400",
"currency": "USD",
"paymentAccountIdentifier": "cash",
"paymentAccountLocalizeInfos": {
"title": "Cash"
},
"products": [
{
"id": 15,
"title": "Orange ball",
"sku": null,
"previewImage": "[]",
"price": 400,
"quantity": 1,
"isGift": false
}
],
"paymentUrl": null,
"discountConfig": {
"orderDiscounts": [],
"productDiscounts": [],
"coupon": null,
"settings": {
"allowStacking": false,
"maxDiscountValue": null,
"allowGiftStacking": false,
"maxBonusPaymentPercent": null,
"minBonusAmount": null,
"minOrderAmountForBonus": null,
"giftRefundPolicy": "KEEP_GIFT"
},
"additionalDiscountsMarkers": [],
"totalRaw": 400,
"totalSumWithDiscount": 400,
"excludedGiftProductIds": [],
"bonus": {
"availableBalance": 0,
"maxBonusDiscount": 0,
"minBonusAmount": null,
"minOrderAmountForBonus": null,
"bonusApplied": 0
},
"bonusApplied": 0,
"totalDue": 400
},
"isPartial": false,
"isCompleted": null,
"split": {
"completed": false,
"partial": false,
"stages": [
{
"marker": "default",
"sessionId": null,
"productId": 15,
"title": "Default",
"value": 400,
"status": "planned"
}
]
}
}

6. Assemble the receipt from the order data

Example:

// currency is frequently an empty string — fall back to '' instead of hardcoding '$'.
const currency = order.currency || '';
// Order status is only a marker; its title is project-specific. Prefer the
// localized title from the API, then a client map, then the raw marker.
const STATUS_LABELS: Record<string, string> = {
inProgress: 'In progress',
completed: 'Completed',
};
const receipt = {
orderId: order.id,
// createdDate is an ISO string returned by the API.
date: new Date(order.createdDate).toLocaleString(),
status:
order.statusLocalizeInfos?.title ??
STATUS_LABELS[order.statusIdentifier ?? ''] ??
order.statusIdentifier,
// paymentAccountLocalizeInfos.title is the human label; fall back to the marker.
payment: order.paymentAccountLocalizeInfos?.title || order.paymentAccountIdentifier,
items: order.products.map((p) => ({
title: p.title,
quantity: p.quantity,
price: `${currency}${p.price.toFixed(2)}`,
lineTotal: `${currency}${(p.price * p.quantity).toFixed(2)}`,
})),
// totalSum is a string ("300.00") — convert before formatting.
total: `${currency}${Number(order.totalSum).toFixed(2)}`,
};
console.log(receipt);
Result:
{
"orderId": 127,
"date": "06.06.2026, 15:04:52",
"status": "Upcoming",
"payment": "Cash",
"items": [
{
"title": "Orange ball",
"quantity": 1,
"price": "USD400.00",
"lineTotal": "USD400.00"
}
],
"total": "USD400.00"
}

7. Render the receipt as a PDF on the client (e.g. with jsPDF)

Example:

/*
import { jsPDF } from 'jspdf';

const doc = new jsPDF();

doc.setFontSize(16);
doc.text(`Receipt #${receipt.orderId}`, 14, 20);

doc.setFontSize(11);
doc.text(`Date: ${receipt.date}`, 14, 30);
doc.text(`Status: ${receipt.status}`, 14, 37);
doc.text(`Payment: ${receipt.payment}`, 14, 44);

let y = 58;
receipt.items.forEach((item) => {
doc.text(`${item.quantity} × ${item.title}`, 14, y);
doc.text(item.lineTotal, 196, y, { align: 'right' });
y += 7;
});

doc.setFontSize(13);
doc.text(`Total: ${receipt.total}`, 196, y + 8, { align: 'right' });

doc.save(`receipt-${receipt.orderId}.pdf`);
*/

Final example

// 1. Import defineOneEntry from SDK and define PROJECT_URL and APP_TOKEN
import { defineOneEntry } from 'oneentry';

const PROJECT_URL = 'your-project-url';
const APP_TOKEN = 'your-app-token';

// 2. Creating an API client with [defineOneEntry()](/docs/index/#Installation)
const { AuthProvider, Orders } = defineOneEntry(PROJECT_URL, {
token: APP_TOKEN,
});

// 3. User authorization with [AuthProvider.auth()](/docs/auth-provider/auth)
const authData = [
{ marker: 'email_reg', value: 'your-email' },
{ marker: 'password_reg', value: 'your-password' },
];
const user = await AuthProvider.auth('email', { authData });
console.log(user);

// 4. Place the order with [Orders.createOrder()](/docs/orders/createOrder)
const body = {
formIdentifier: 'order',
paymentAccountIdentifier: 'cash',
formData: [{ type: 'string', marker: 'name', value: 'Christina Thomas' }],
products: [{ productId: 15, quantity: 1 }],
};
const created = await Orders.createOrder('orders', body as any);

if ('statusCode' in created) {
throw new Error(created.message);
}

// 5. Read the placed order back with [Orders.getOrderByMarkerAndId()](/docs/orders/getOrderByMarkerAndId)
// This returns the full order: products with titles/prices, totalSum, currency,
// payment method and status — everything the receipt needs.
const order = await Orders.getOrderByMarkerAndId('orders', created.id);

if ('statusCode' in order) {
throw new Error(order.message);
}

// 6. Assemble the receipt from the order data
// currency is frequently an empty string — fall back to '' instead of hardcoding '$'.
const currency = order.currency || '';
// Order status is only a marker; its title is project-specific. Prefer the
// localized title from the API, then a client map, then the raw marker.
const STATUS_LABELS: Record<string, string> = {
inProgress: 'In progress',
completed: 'Completed',
};
const receipt = {
orderId: order.id,
// createdDate is an ISO string returned by the API.
date: new Date(order.createdDate).toLocaleString(),
status:
order.statusLocalizeInfos?.title ??
STATUS_LABELS[order.statusIdentifier ?? ''] ??
order.statusIdentifier,
// paymentAccountLocalizeInfos.title is the human label; fall back to the marker.
payment: order.paymentAccountLocalizeInfos?.title || order.paymentAccountIdentifier,
items: order.products.map((p) => ({
title: p.title,
quantity: p.quantity,
price: `${currency}${p.price.toFixed(2)}`,
lineTotal: `${currency}${(p.price * p.quantity).toFixed(2)}`,
})),
// totalSum is a string ("300.00") — convert before formatting.
total: `${currency}${Number(order.totalSum).toFixed(2)}`,
};
console.log(receipt);

// 7. Render the receipt as a PDF on the client (e.g. with jsPDF)
/*
import { jsPDF } from 'jspdf';

const doc = new jsPDF();

doc.setFontSize(16);
doc.text(`Receipt #${receipt.orderId}`, 14, 20);

doc.setFontSize(11);
doc.text(`Date: ${receipt.date}`, 14, 30);
doc.text(`Status: ${receipt.status}`, 14, 37);
doc.text(`Payment: ${receipt.payment}`, 14, 44);

let y = 58;
receipt.items.forEach((item) => {
doc.text(`${item.quantity} × ${item.title}`, 14, y);
doc.text(item.lineTotal, 196, y, { align: 'right' });
y += 7;
});

doc.setFontSize(13);
doc.text(`Total: ${receipt.total}`, 196, y + 8, { align: 'right' });

doc.save(`receipt-${receipt.orderId}.pdf`);
*/