Use external shipping frame
Overview
Learn how to implement a checkout flow using an external shipping provider frame such as nShift. This allows customers to select pickup points, delivery times, and other shipping options directly within an embedded widget.
Prerequisites
- Merchant API key
- Existing cart with items
- External shipping provider configured (e.g., nShift)
- Customer's zip/postal code
Goal
- Create a checkout session with basic customer information
- Initialize the external shipping frame with zip code
- Display the shipping widget and capture customer selections
- Update checkout with selected shipping options
Architecture at a glance
- Create checkout → Initialize shipping frame with zip → Display widget → Capture selections → Update checkout
Step-by-step
Create checkout session
Start by creating a checkout session.
Request example
mutation createOrUpdateCheckout(
$cartId: String!
$checkout: CheckoutInputType
$channelId: String
$languageId: String
$marketId: String
) {
createOrUpdateCheckout(
cartId: $cartId
checkout: $checkout
channelId: $channelId
languageId: $languageId
marketId: $marketId
) {
cart {
id
summary {
total {
regularPriceIncVat
}
}
}
shippingData
}
}
{
"Accept": "application/json",
"X-ApiKey": "{MERCHANT_API_KEY}"
}
{
"cartId": "{CART_ID}",
"channelId": "{CHANNEL_ID}",
"languageId": "{LANGUAGE_ID}",
"marketId": "{MARKET_ID}"
}
curl -X POST https://merchantapi.geins.io/graphql \
-H "Accept: application/json" \
-H "Content-Type: application/json" \
-H "X-ApiKey: {MERCHANT_API_KEY}" \
-d '{"query":"mutation createOrUpdateCheckout($cartId: String!, $checkout: CheckoutInputType, $channelId: String, $languageId: String, $marketId: String) { createOrUpdateCheckout(cartId: $cartId, checkout: $checkout, channelId: $channelId, languageId: $languageId, marketId: $marketId) { cart { id summary { total { regularPriceIncVat } } } shippingData }","variables":{"cartId":"{CART_ID}","channelId":"{CHANNEL_ID}","languageId":"{LANGUAGE_ID}","marketId":"{MARKET_ID}"}}'
Response example
200 OK{
"data": {
"createOrUpdateCheckout": {
"cart": {
"id": "{CART_ID}",
"summary": {
"total": {
"regularPriceIncVat": 299.00
}
}
},
"shippingData": null
}
}
}
Supply zip code to initialize shipping frame
Update the checkout with the customer's zip/postal code to initialize the external shipping frame.
Request example
mutation createOrUpdateCheckout(
$cartId: String!
$checkout: CheckoutInputType
$channelId: String
$languageId: String
$marketId: String
) {
createOrUpdateCheckout(
cartId: $cartId
checkout: $checkout
channelId: $channelId
languageId: $languageId
marketId: $marketId
) {
shippingData
}
}
{
"Accept": "application/json",
"X-ApiKey": "{MERCHANT_API_KEY}"
}
{
"cartId": "{CART_ID}",
"checkout": {
"billingAddress": {
"zip": "{ZIP_CODE}",
}
},
"channelId": "{CHANNEL_ID}",
"languageId": "{LANGUAGE_ID}",
"marketId": "{MARKET_ID}"
}
curl -X POST https://merchantapi.geins.io/graphql \
-H "Accept: application/json" \
-H "Content-Type: application/json" \
-H "X-ApiKey: {MERCHANT_API_KEY}" \
-d '{"query":"mutation createOrUpdateCheckout($cartId: String!, $checkout: CheckoutInputType, $channelId: String, $languageId: String, $marketId: String) { createOrUpdateCheckout(cartId: $cartId, checkout: $checkout, channelId: $channelId, languageId: $languageId, marketId: $marketId) { shippingData }","variables":{"cartId":"{CART_ID}","checkout":{"billingAddress":{"zip":"{ZIP_CODE}"}},"channelId":"{CHANNEL_ID}","languageId":"{LANGUAGE_ID}","marketId":"{MARKET_ID}"}}'
Response example
200 OK{
"data": {
"createOrUpdateCheckout": {
"shippingData": "<div id=\"nshift-checkout\"><!-- NShift iframe HTML --></div><script>/* NShift script */</script>"
}
}
}
Display the external shipping widget
Embed the external shipping provider's widget in your checkout page. The exact implementation depends on your shipping provider.
Update checkout with selected shipping data
After the customer selects a delivery option in the widget, update the checkout with the selection details, this is different depending on your shipping provider.
Request variables example
{
"cartId": "{CART_ID}",
"checkout": {
"billingAddress": {
"zip": "{ZIP_CODE}",
},
"externalShippingId": "12345",
"pickupPoint": "12345_67899",
"message": "Delivery details: Pickup Point"
},
"channelId": "{CHANNEL_ID}",
"languageId": "{LANGUAGE_ID}",
"marketId": "{MARKET_ID}"
}
Options
Multi-market support
All mutations support optional parameters for multi-market functionality:
channelId: Target specific sales channelslanguageId: Set content languagemarketId: Target specific markets
Authenticated access
While authentication is not required for this mutation, including a JWT bearer token in the Authorization header can provide personalized results based on the authenticated user's context, for example personalized pricing.
To include authentication, add the JWT bearer token to your request headers:
"Authorization": "Bearer {JWT_TOKEN}"
Common pitfalls
- Ensure the zip/postal code format matches what the shipping provider expects
- The external shipping widget must be properly configured in your Geins backend