External Order Integration
Learn how to create subscription orders from external systems like telesales or automated order processing.
Overview
The Vendor Order API allows authorized vendors to programmatically insert subscription orders into the Sesamy platform. This is typically used by telesales (TM) teams or automated order processing systems that need to create customer contracts via API.
Getting Started
Before using this API, you need to obtain from Sesamy:
- OAuth2 Client Credentials - Client ID, Client Secret, and the
paymentsContractThirdPartyOnboardingscope - Vendor Configuration - Your
vendorIdand promotional codes (promoCode) configured for your vendor
INFO
Contact Sesamy to set up your integration credentials and promo codes.
Promo Codes
A promo code represents a specific product at a specific price. Each offer you want to make available via the API requires its own promo code to be configured in Sesamy.
For example, if you want to offer:
- A 12-month digital subscription at 99 kr/month
- A 6-month digital subscription at 119 kr/month
- A print + digital bundle at 149 kr/month
Each of these would need a separate promo code.
To set up promo codes:
- List all the offers you want to make available (product, price, billing period)
- Send the list to Sesamy for configuration
- Sesamy will provide the corresponding promo codes to use in your API requests
Authentication
The API uses OAuth2 Client Credentials flow.
Obtain Access Token
curl -X POST https://token.sesamy.com/oauth/token \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "grant_type=client_credentials" \
-d "client_id=YOUR_CLIENT_ID" \
-d "client_secret=YOUR_CLIENT_SECRET" \
-d "scope=paymentsContractThirdPartyOnboarding"Response:
{
"access_token": "eyJhbGc...",
"token_type": "Bearer",
"expires_in": 3600
}Include the access token in the Authorization header of all API requests:
Authorization: Bearer YOUR_ACCESS_TOKENCreating Orders
Endpoint
POST https://api.sesamy.com/payments/vendor/{vendorId}/promos/code/{promoCode}?confirm=true
Creates a new subscription contract for a customer using a promotional code. The confirm=true parameter creates and confirms the contract in a single request.
TIP
Use ?confirm=true to create and confirm contracts in one step, reducing round trips.
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
vendorId | string | Yes | Your vendor identifier |
promoCode | string | Yes | The promotional code for the subscription offer |
Query Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
confirm | boolean | No | Set to true to confirm the contract immediately |
Request Body
{
"externalOrderId": "ORDER-2025-001234",
"quantity": 1,
"paymentMethod": "INVOICE",
"paymentProvider": "BILLOGRAM",
"startDate": "2025-01-08",
"userData": {
"email": "customer@example.com",
"fullName": "John Doe",
"phone": "+46701234567",
"address": {
"firstName": "John",
"lastName": "Doe",
"street": "Example Street 123",
"zip": "12345",
"city": "Stockholm",
"country": "SE"
},
"extraData": {
"flowyCustomerNumber": "987654321",
"seller": "Jane Smith",
"leadSourceName": "Winter Campaign 2025"
}
},
"vendorData": {
"promoCode": "PROMOCODE",
"seller": "tm-team",
"sellerRequestId": "987654321"
}
}Request Body Schema
| Field | Type | Required | Description |
|---|---|---|---|
externalOrderId | string | Yes | Your unique order identifier |
quantity | number | No | Number of subscriptions (default: 1) |
paymentMethod | string | Yes | Payment method: INVOICE, CARD, SWISH |
paymentProvider | string | Yes | Payment provider: BILLOGRAM, STRIPE |
startDate | string | No | Contract start date (YYYY-MM-DD) |
userData | object | Yes | End user/subscriber information |
userData.email | string | Yes | Customer email address |
userData.fullName | string | No | Customer full name |
userData.phone | string | No | Customer phone number |
userData.address | object | No | Customer address |
userData.address.country | string | No | Country code (ISO 3166-1 alpha-2) |
userData.extraData | object | No | Additional custom data |
ownerData | object | No | Payer information (if different from user) |
vendorData | object | No | Vendor-specific metadata |
INFO
If ownerData is not provided, the system assumes the user is also the payer.
Response
Status: 200 OK
{
"contractId": "f1dc9c2a-bf9f-4151-ab98-443c02280df9",
"responseKey": "CONTRACT_CREATED_AND_CONFIRMED"
}| Field | Type | Description |
|---|---|---|
contractId | string | Unique identifier for the created contract |
responseKey | string | Status of the operation |
delayedContractStartsAt | string | Start date if contract is delayed |
Response Keys:
| Key | Description |
|---|---|
CONTRACT_CREATED | Contract created but not confirmed |
CONTRACT_CREATED_AND_CONFIRMED | Contract created and confirmed successfully |
SKIPPED_ALREADY_CONFIRMED | Contract was already confirmed |
Complete Example
# 1. Get access token
ACCESS_TOKEN=$(curl -s -X POST https://token.sesamy.com/oauth/token \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "grant_type=client_credentials" \
-d "client_id=YOUR_CLIENT_ID" \
-d "client_secret=YOUR_CLIENT_SECRET" \
-d "scope=paymentsContractThirdPartyOnboarding" | jq -r '.access_token')
# 2. Create and confirm order
curl -X POST "https://api.sesamy.com/payments/vendor/YOUR_VENDOR_ID/promos/code/PROMOCODE?confirm=true" \
-H "Authorization: Bearer $ACCESS_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"externalOrderId": "ORDER-2025-001234",
"quantity": 1,
"paymentMethod": "INVOICE",
"paymentProvider": "BILLOGRAM",
"startDate": "2025-01-08",
"userData": {
"email": "customer@example.com",
"fullName": "John Doe",
"phone": "+46701234567",
"address": {
"firstName": "John",
"lastName": "Doe",
"street": "Example Street 123",
"zip": "12345",
"city": "Stockholm",
"country": "SE"
}
},
"vendorData": {
"promoCode": "PROMOCODE",
"seller": "tm-team"
}
}'Error Handling
Common Errors
| Error | Status | Cause | Solution |
|---|---|---|---|
UserEmailRequiredError | 400 | Missing userData.email | Provide customer email |
InvalidAddressError | 400 | Invalid address format | Verify country code is ISO 3166-1 alpha-2 |
Unauthorized | 401 | Invalid or expired token | Obtain a new access token |
Forbidden | 403 | Client not authorized for vendor | Verify vendorId matches your credentials |
PromoCodeNotFoundError | 404 | Invalid promo code | Verify promo code with Sesamy |
ConflictError | 409 | Duplicate externalOrderId | Use a unique order ID |
InvalidSMNOError | 422 | Non-numeric vendorData.SMNO | Use only numbers for SMNO |
Error Response Format
{
"error": "UserEmailRequiredError",
"message": "User email is required for promo contract creation"
}Best Practices
Use unique order IDs - Always use a unique
externalOrderIdfor each order to prevent duplicatesValidate data before sending - Validate on your side to reduce errors:
- Email format
- Phone number format
- Country codes (ISO 3166-1 alpha-2)
Handle token expiry - Tokens expire after 1 hour. Implement refresh logic.
Check before retrying - If you receive a network error, check if the order was created before retrying to avoid duplicates
Log responses - Log all API responses with the
externalOrderIdfor troubleshooting
Troubleshooting
Order Not Created
- Verify your access token is valid and not expired
- Check that the
vendorIdmatches your OAuth2 client configuration - Ensure the promo code is configured for your vendor
Duplicate Order Error
- Check if an order with the same
externalOrderIdalready exists - Use a unique identifier for each new order
Authentication Failed
- Verify your client credentials
- Ensure you're requesting the correct scope:
paymentsContractThirdPartyOnboarding
Next Steps
- Managing Subscriptions - Subscription lifecycle management
- Handling Webhooks - Receive notifications for order events
- Authentication - Learn more about OAuth2 authentication
- API Reference - Explore available API endpoints