CarrierService

A carrier service (also known as a carrier calculated service or shipping service) provides real-time shipping rates to Shopify. Some common carrier services include Canada Post, FedEx, UPS, and USPS. The term carrier is often used interchangeably with the terms shipping company and rate provider.

Using the CarrierService resource, you can add a carrier service to a shop and then provide a list of applicable shipping rates at checkout. You can even use the cart data to adjust shipping rates and offer shipping discounts based on what is in the customer’s cart.

Requirements for accessing the CarrierService resource

To access the CarrierService resource, add the write_shipping permission to your app’s requested scopes. For more information, see API access scopes.

Your app’s request to create a carrier service will fail unless the store installing your carrier service meets one of the following requirements:

  • It is on the Advanced Shopify plan or higher.
  • Its Shopify plan is paid annually.
  • It is a development store.

Note

If a store changes its Shopify plan, then the store’s association with a carrier service is deactivated if the store no long meets one of the requirements above.

Providing shipping rates to Shopify

When adding a carrier service to a store, you need to provide a POST endpoint rooted in the callback_url property where Shopify can retrieve applicable shipping rates. The callback URL should be a public endpoint that expects these requests from Shopify.

A sample Shopify request for shipping rates:

POST

Your callback URL

Retrieves a list of applicable shipping rates

Example shipping rate request sent to a carrier service

{

“rate”: {

  1. "origin": {
  2. "country": "CA",
  3. "postal_code": "K2P1L4",
  4. "province": "ON",
  5. "city": "Ottawa",
  6. "name": null,
  7. "address1": "150 Elgin St.",
  8. "address2": "",
  9. "address3": null,
  10. "phone": "16135551212",
  11. "fax": null,
  12. "email": null,
  13. "address_type": null,
  14. "company_name": "Jamie D's Emporium"
  15. },
  16. "destination": {
  17. "country": "CA",
  18. "postal_code": "K1M1M4",
  19. "province": "ON",
  20. "city": "Ottawa",
  21. "name": "Bob Norman",
  22. "address1": "24 Sussex Dr.",
  23. "address2": "",
  24. "address3": null,
  25. "phone": null,
  26. "fax": null,
  27. "email": null,
  28. "address_type": null,
  29. "company_name": null
  30. },
  31. "items": [{
  32. "name": "Short Sleeve T-Shirt",
  33. "sku": "",
  34. "quantity": 1,
  35. "grams": 1000,
  36. "price": 1999,
  37. "vendor": "Jamie D's Emporium",
  38. "requires_shipping": true,
  39. "taxable": true,
  40. "fulfillment_service": "manual",
  41. "properties": null,
  42. "product_id": 48447225880,
  43. "variant_id": 258644705304
  44. }],
  45. "currency": "USD",
  46. "locale": "en"

}

}

View Response

The address3, fax, address_type, and company_name fields are returned by specific ActiveShipping providers. For API-created carrier services, you should use only the following shipping address fields:

  • address1
  • address2
  • city
  • zip
  • province
  • country

Other values remain as null and are not sent to the callback URL.

Response fields

When Shopify requests shipping rates using your callback URL, the response object rates must be a JSON array of objects with the following fields. Required fields must be included in the response for the carrier service integration to work properly.

Field Description
service_name
REQUIRED
The name of the rate, which customers see at checkout. For example: Expedited Mail
.
description
REQUIRED
A description of the rate, which customers see at checkout. For example: Includes tracking and insurance
.
service_code
REQUIRED
A unique code associated with the rate. For example: expedited_mail
.
currency
REQUIRED
The currency of the shipping rate.
total_price
REQUIRED
The total price expressed in subunits. If the currency does not use subunits, the value must be multiplied by 100. For example: "total_price": 500 for 5.00 CAD, "total_price": 100000 for 1000 JPY.
phone_required Whether the customer must provide a phone number at checkout.
min_delivery_date The earliest delivery date for the displayed rate.
max_delivery_date The latest delivery date for the displayed rate to still be valid.

Response Timeouts

The read timeout for rate requests are dynamic, based on the number of requests per minute (RPM). These limits are applied to each shop-app pair. The timeout values are as follows.

RPM Range Timeout
Under 1500 10s
1500 to 3000 5s
Over 3000 3s

Note: These values are upper limits and should not be interpretted as a goal to develop towards. Shopify is constantly evaluating the performance of the platform and working towards improving resilience as well as app capabilities. As such, these numbers may be adjusted outside of our normal versioning timelines.

Server-side caching of requests

Shopify provides server-side caching to reduce the number of requests it makes. Any shipping rate request that identically matches the following fields will be retrieved from Shopify’s cache of the initial response:

  • variant IDs
  • default shipping box weight and dimensions
  • variant quantities
  • carrier service ID
  • origin address
  • destination address
  • item weights and signatures

If any of these fields differ, or if the cache has expired since the original request, then new shipping rates are requested. The cache expires 15 minutes after rates are successfully returned. If an error occurs, then the cache expires after 30 seconds.

What you can do with CarrierService

The Shopify API lets you do the following with the CarrierService resource. More detailed versions of these general actions may be available:

CarrierService properties

active plain "active": true Whether this carrier service is active.
callback_url plain "callback_url": "http://myapp.com" The URL endpoint that Shopify needs to retrieve shipping rates. This must be a public URL.
carrier_service_type plain "carrier_service_type": "api" Distinguishes between API or legacy carrier services.
id plain "id": 14079244 The ID of the carrier service.
format plain "format": "json" The format of the data returned by the URL endpoint. Valid values: json and xml. Default value: json.
name plain "name": "My Carrier Service" The name of the shipping service as seen by merchants and their customers.
service_discovery plain "service_discovery": true Whether merchants are able to send dummy data to your service through the Shopify admin to see shipping rate examples.
admin_graphql_api_id plain "admin_graphql_api_id": "gid://shopify/DeliveryCarrierService/1" The GraphQL unique identifier for the carrier service.

Endpoints

POST/admin/api/2021-01/carrier_services.json Creates a carrier service

Create a carrier service

POST /admin/api/2021-01/carrier_services.json

{

“carrier_service”: {

"name": "Shipping Rate Provider",

"callback_url": "http://shippingrateprovider.com",

"service_discovery": true

}

}

View Response

PUT/admin/api/2021-01/carrier_services/{carrier_service_id}.json

Updates a carrier service. Only the app that creates a carrier service can update it.

Update a carrier service

PUT /admin/api/2021-01/carrier_services/1036894960.json

{

“carrier_service”: {

"id": 1036894960,

"name": "Some new name",

"active": false

}

}

View Response

GET/admin/api/2021-01/carrier_services.json Retrieves a list of carrier services

Retrieve a list of carrier services

GET /admin/api/2021-01/carrier_services.json

View Response

GET/admin/api/2021-01/carrier_services/{carrier_service_id}.json

Retrieves a single carrier service by its ID

Retrieve a single carrier service

GET /admin/api/2021-01/carrier_services/1036894955.json

View Response

DELETE/admin/api/2021-01/carrier_services/{carrier_service_id}.json

Deletes a carrier service

Delete a carrier service

DELETE /admin/api/2021-01/carrier_services/1036894956.json

View Response