Checkout Testimony Offer
Initiate Stripe checkout for a testimony offer. This endpoint creates a Stripe checkout session and returns a URL where the client can complete payment. The client pays the offer price; the platform commission is deducted from the expert's payout, not added on top.
Complete Payment Guide
See Payment Integration for the complete payment flow guide.
HTTP Request
POST /api/v1/testimonies/offers/:offerId/checkout
Parameters
| Parameter | Description |
|---|---|
phone string | Phone number in international format with country code (e.g., +421901234567). Must not be used by another user; the client's own current number is accepted. See Phone Numbers. |
firstName string | Client's first name (max 255 chars). |
lastName string | Client's last name (max 255 chars). |
billingAddress object, Address | Billing address for the payment. |
shippingAddress object, Address, optional | Delivery address, stored with the client's firstName/lastName. Not sent to Stripe (the billing address is). When omitted, the client's stored shipping address is left unchanged. |
company object, CheckoutCompany, optional | Company information for business purchases. |
The submitted phone, firstName, lastName, billingAddress, shippingAddress and company are saved to the client's profile — the same data as Update Current User.
Address Object
| Field | Type | Required | Description |
|---|---|---|---|
firstName | string | No | Contact's first name (for shipping addresses only). |
lastName | string | No | Contact's last name (for shipping addresses only). |
line1 | string | Yes | Street address (e.g., "Trieda Andreja Hlinku"). Max 255 characters. |
line2 | string | Yes | Additional address info (e.g., unit number). Must be a non-empty string — "" and null are rejected. Max 255 characters. |
city | string | Yes | City name. Max 255 characters. |
postalCode | string | Yes | Postal code. Max 255 characters. |
country | string | Yes | ISO 3166-1 Alpha-2 country code (e.g., SK, CZ, HU). |
Address Types
- Billing Address: Contains core address fields only (no name fields)
- Shipping Address: Includes optional
firstNameandlastNamefields for delivery contact - Checkout Address: All fields have a maximum length of 255 characters
Example (Shipping Address):
{
"firstName": "Anton",
"lastName": "Čomáš",
"line1": "Trieda Andreja Hlinku",
"line2": "1/14A",
"city": "Nitra",
"postalCode": "949 01",
"country": "SK"
}Example (Billing Address):
{
"line1": "Trieda Andreja Hlinku",
"line2": "1/14A",
"city": "Nitra",
"postalCode": "949 01",
"country": "SK"
}CheckoutCompany Object
| Attribute | Description |
|---|---|
businessId string | Company business ID (max 255 chars). |
taxId string | Company tax ID (max 255 chars). |
vatId string, optional | VAT ID if applicable (max 255 chars). |
Response
200 OK
Returns a JSON object with the Stripe checkout URL.
{
"data": {
"url": "https://checkout.stripe.com/c/pay/cs_test_a1..."
}
}Next Steps:
- Redirect user to
urlto complete payment on Stripe - After payment, Stripe redirects back to the success URL configured on the backend with
?sessionId={sessionId}appended (the cancel URL receives the same parameter) - Call Accept Offer with the session ID to complete the process
Calling this endpoint again for the same testimony (for any of its offers) returns a new URL and expires the previously issued, still-open Stripe session — always use the most recent URL.
Error Handling
Validation Errors
422 Unprocessable Content
{
"message": "Telefónne číslo už existuje.",
"errors": {
"phone": [
"Telefónne číslo už existuje."
]
}
}Returned when:
- Phone number is used by another user
- Phone number is not a valid international number
- Required fields are missing or invalid (
line2must be a non-empty string)
Business Errors
422 Unprocessable Content with a plain message:
Platbu je možné začať len pri posudku s aktívnou ponukou.— the testimony is no longeroffered(cancelled, or another offer was already paid)Znalec ešte nie je overený.— the offer's expert has not been approved yetPri spracovaní platby nastala chyba. Skúste to znova.— Stripe rejected the request
Rate Limit
429 Too Many Requests — more than 3 checkout attempts per minute for this user.
Payment Initialization Failed
500 Internal Server Error
{
"message": "An unexpected error occurred."
}Returned when the Stripe checkout session cannot be created due to a system error.
Authentication
Requires authentication via Bearer token and a verified email.
401 Unauthorized
{
"message": "Unauthenticated."
}Requirements
- Authentication: Bearer token required, email verified
- Role: Client only — and the testimony must belong to the client (
403 Forbiddenotherwise) - Testimony State: Must be in
offeredstate - Expert: The offer's expert must be approved
- Phone: Must not belong to another user
Notes
- Creates a Stripe checkout session for the offer
price; the platform commission (21%) is taken from the expert's share — see Offer Object - Phone number must be unique across all users