Fulfillment nshift
nShift Checkout fulfillment provider plugin for Medusa V2
@solteq-excom/medusa-fulfillment-nshift
nShift Checkout fulfillment provider for Medusa v2.
Brings nShift's delivery options into a Medusa storefront: real carrier options, real prices for the customer's address and basket, and a partial shipment created in nShift when the order is fulfilled.
- Dynamic delivery options — the options an admin can attach to a shipping option come straight from your nShift Checkout configuration.
- Calculated pricing — prices are fetched per cart, using the receiver address, package weight/volume and basket value, so nShift price rules (free shipping thresholds, weight bands, per-country pricing) apply.
- Pickup points, time slots and addons — selected at checkout, validated against nShift, and forwarded to the shipment.
- Partial shipments — created on fulfillment, deleted again when the fulfillment is cancelled.
- Fails soft — if nShift is unreachable or does not offer an option for a cart, that option is simply reported as unavailable. Checkout keeps working.
- Token and session handling — OAuth2 tokens are cached and refreshed; one nShift session is reused across all the options of a cart.
Requirements
- Medusa
- Node
- An active nShift Checkout agreement
Installation
nShift account setup
- Log in to the nShift Portal.
- Settings → API Configuration → Clients → Add. Give the client the Public checkout API scope and copy the Client ID and Client Secret (the secret is only shown once).
- Connections — copy the Connection ID you want Medusa to use.
- Configure the Checkout configuration behind that connection with the carriers and delivery options you want to offer.
Configuration
Register the provider on the Fulfillment Module, and register the plugin so its build output is loaded:
Define the Fulfillment Module once. If it appears twice in , the last definition wins and the provider in the earlier one is never registered — which makes every cart that references an nShift shipping option fail.
If your client secret contains , do not escape it as in — dotenv keeps the backslash and nShift answers . Wrap the value in quotes instead.
Provider options
| Option | Type | Default | Description |
|---|---|---|---|
| — | Required. nShift API Client ID. | ||
| — | Required. nShift API Client Secret. | ||
| — | Required. nShift Checkout Connection ID. | ||
| Language for option names and descriptions (ISO 639). | |||
| Locale for formatted price/date strings. | |||
| — | Country used to list delivery options in the admin (ISO 3166-1 alpha-2). Required for the admin dropdown. | ||
| — | Postal code used to list delivery options in the admin. Required for the admin dropdown. | ||
| — | State/province sent when the Medusa address has none. Some markets need it. | ||
| Currency used when the calculation context carries none. | |||
| Whether nShift prices already include tax. | |||
| Unit of in your data. Set to if you store grams. | |||
| Unit of / / . | |||
| Weight sent when no item weights are known. | |||
| Send the basket value as so nShift price rules can evaluate. | |||
| Push partial shipments to your Book & Print platform. | |||
| Count sessions towards nShift's conversion-rate metric. | |||
| Per-request timeout against the nShift API. | |||
| How long one session and its delivery options are reused for an unchanged cart. | |||
| Override the nShift API host. | |||
| Override the nShift token endpoint. |
Check . Medusa does not define a unit for . The default matches earlier versions of this plugin; if your catalogue stores grams, set or nShift will price a 500 g shirt as 500 kg.
Check . nShift Checkout prices are normally the consumer-facing gross price, hence the default. Set it to if your configuration holds net prices, otherwise your cart's tax totals will be wrong.
Creating shipping options in the admin
- Settings → Locations & Shipping → your location → Shipping options → Create.
- Set Price type to Calculated so the price comes from nShift.
- Pick nShift as the provider and choose one of the delivery options it lists. Each Medusa shipping option maps to exactly one nShift delivery option.
The chosen delivery option is stored on . If that dropdown is empty or errors, the message tells you why — most often a missing / , or no delivery options configured for that country.
Storefront usage
Calculated options come back from without a price; fetch each price with , then add the method to the cart.
accepted when adding a shipping method
Both snake_case and the nShift widget's camelCase spelling are accepted.
| Key | Alias | Description |
|---|---|---|
| A from the option's . | ||
| A from the option's . | ||
| — | , or . | |
| Shorthand: . | ||
| — | or a map. |
Selections are validated against the delivery option before the method is stored: an unknown pickup point, time slot or addon is rejected with a naming it. Addon prices are added to the shipping price.
Anything else you put in is preserved verbatim, so you can carry your own state through checkout.
What ends up on the shipping method
After fulfillment, additionally carries , , and .
Behaviour and error handling
The provider never breaks a cart. reports an option as unavailable — no — instead of throwing, whenever:
- the cart has no country or postal code yet,
- nShift does not return the option for that address (wrong country route, weight over the limit, a price rule excluding it),
- nShift returns the option without a price,
- the nShift API is unreachable, times out or errors,
- the shipping option has no nShift delivery option attached.
Medusa treats a missing price as "not available in this context": removes the shipping method, and an explicit selection is rejected with . So changing the shipping country to one a carrier does not serve drops that method rather than failing the address update. Every case is logged with the nShift status and so you can see the reason in the server log.
Errors are raised where they are actionable instead:
| Situation | Result |
|---|---|
| Missing / / | throws at startup |
| Admin option list without / | naming the missing option |
| Admin option list, nShift request fails | including the nShift status and issues |
| Selecting an option nShift no longer offers | , pick another method |
| Unknown pickup point, time slot or addon | naming it |
| Option requires a pickup point and none was sent | |
| Fulfilling without checkout session data | |
| Order address nShift cannot ship to | |
| nShift refuses to delete a cancelled shipment | logged, cancellation still succeeds |
Not covered yet
- Split shipments (nShift's endpoints).
- Return shipments — is not implemented.
- Labels and tracking numbers: booking and printing still happen in your Book & Print platform, so returns no .
- Own Pickup Locations API management.
- Badges, certifications and Klarna delivery types are read from nShift but not surfaced on the shipping method.
License
MIT

