Our Help Center has a fresh new feel.

We've made it easier to browse, search, and get to the information you need. Use the left navigation menu to explore by topic, or search for something specific.

API: Managing Pricing

The Storefront API lets you retrieve and update your pricing configuration programmatically — TLD pricing, add-on pricing, currencies, default markup, price rounding, and tax rules — without logging into Storefront Manager. This is useful for feeding pricing data into your own billing or reporting systems, or managing your pricing configuration from your own tooling.

Before you begin

Requirements

  • An active OpenSRS Storefront with API access enabled
  • API credentials (Client ID and Client Secret) — see API DNS Management Guide for how to generate these and obtain an access token. Pricing uses the same OAuth 2.0 Client Credentials flow, the same base URLs, and the same 600 requests/minute rate limit as DNS — no separate setup needed.
  • Your OpenSRS account balance above $10 to keep your Storefront active

The login ID header

Most endpoints below accept an optional x-osrs-system-login-id header — the ID of the specific login to act as, needed only if your reseller account has more than one login to choose from. If you only have one, you can omit it.

curl -X GET "https://api.shopco.com/v1/tlds" \  -H "Authorization: Bearer <access_token>" \  -H "x-osrs-system-login-id: <login_id>"

TLD endpoints

List your TLD catalogue

Returns every TLD available to you, with its current pricing configuration — not just TLDs you've enabled.

GET /v1/tlds

Example cURL

curl -X GET "https://api.shopco.com/v1/tlds" \  -H "Authorization: Bearer <access_token>"

Example response

200 OK — an array of TLD entries.

[  {    "name": "com",    "true_tld": "com",    "status": "custom_pricing",    "markup": 20,    "retail_price": 14.99,    "osrs_price": 9.99,    "currency_code": "USD",    "currency_symbol": "$"  } ]
FieldDescription
nameThe TLD
true_tldUnderlying TLD identifier
statusPricing status (e.g. custom_pricing)
markupCurrent markup percentage
retail_priceWhat your customers are charged
osrs_priceOpenSRS's underlying cost
currency_code / currency_symbolCurrency this row is priced in

Note: this endpoint doesn't currently support filtering by TLD type or pagination — it returns your full catalogue in one response.


Get pricing for a TLD

Returns the pricing strategy and cost basis for one TLD, broken out by operation.

GET /v1/tld/{tld}/pricing

Path parameters

ParameterTypeDescription
tldstringThe top-level domain, e.g. com

Example cURL

curl -X GET "https://api.shopco.com/v1/tld/com/pricing" \  -H "Authorization: Bearer <access_token>"

Example response

200 OK

{  "registration": "custom_markup",  "registration_custom_markup": 20,  "registration_custom_final_price": null,  "transfer": "same_as_registration",  "transfer_custom_markup": null,  "transfer_custom_final_price": null,  "renew": "same_as_registration",  "renew_custom_markup": null,  "renew_custom_final_price": null,  "redemption": "default",  "redemption_custom_markup": null,  "redemption_custom_final_price": null,  "registration_osrs": 9.99,  "transfer_osrs": 9.99,  "renew_osrs": 9.99,  "redemption_osrs": 79.99 }

Each operation — registration, transfer, renew, redemption — has its own pricing strategy:

StrategyMeaning
defaultUse your storefront's default markup
custom_markupA specific markup percentage for this TLD and operation (see <operation>_custom_markup)
custom_final_priceA fixed price you set directly, in USD plus any other configured currencies (see <operation>_custom_final_price)
same_as_registrationTransfer, renew, and redemption only — mirrors whatever registration is set to

<operation>_osrs fields report OpenSRS's underlying cost for that operation, regardless of strategy.

Note: pricing here is per operation and per currency — there's no separate rate for different registration term lengths (1 year vs. multi-year).


Set pricing on TLDs

Applies one pricing configuration to one or more TLDs in a single request.

POST /v1/tlds/set_pricing

Request fields

FieldTypeRequiredDescription
tldsarray of stringsYesTLDs to apply this pricing to
registrationstringYesdefault, custom_markup, or custom_final_price
registration_custom_markupinteger (0–999)If registration is custom_markupPercent
registration_custom_final_priceobjectIf registration is custom_final_price{"usd_price": <number>, "foreign_currency_prices": [{"currency_code": "CAD", "price": <number>}, ...]}
transfer / renew / redemptionstringYes / Yes / NoSame options as registration, plus same_as_registration
transfer_custom_markup, renew_custom_markup, redemption_custom_markupinteger (0–999)If that operation is custom_markupPercent
transfer_custom_final_price, renew_custom_final_price, redemption_custom_final_priceobjectIf that operation is custom_final_priceSame shape as above
enable_tldsbooleanNo, default trueAlso enable the given TLDs at the same time

Note: this applies the same pricing to every TLD in the tlds array in one call — it doesn't accept different prices per TLD. To price TLDs differently, send separate requests.

Example request

{  "tlds": ["com", "net"],  "registration": "custom_markup",  "registration_custom_markup": 20,  "transfer": "same_as_registration",  "renew": "same_as_registration",  "redemption": "default",  "enable_tlds": true }

Example cURL

curl -X POST "https://api.shopco.com/v1/tlds/set_pricing" \  -H "Authorization: Bearer <access_token>" \  -H "Content-Type: application/json" \  -d '{    "tlds": ["com", "net"],    "registration": "custom_markup",    "registration_custom_markup": 20,    "transfer": "same_as_registration",    "renew": "same_as_registration",    "redemption": "default",    "enable_tlds": true  }'

Response: 200 OK


Enable or disable TLDs

Turns one or more TLDs on or off for your storefront in a single request.

POST /v1/tlds/set_enabled_status

Request fields

FieldTypeRequiredDescription
tldsarray of stringsYesTLDs to update
enabledbooleanYestrue to enable, false to disable

Example cURL

curl -X POST "https://api.shopco.com/v1/tlds/set_enabled_status" \  -H "Authorization: Bearer <access_token>" \  -H "Content-Type: application/json" \  -d '{ "tlds": ["org"], "enabled": true }'

Response: 200 OK


Get TLD status

Checks whether a single TLD is enabled on your storefront.

GET /v1/tld/{tld}/status

Example cURL

curl -X GET "https://api.shopco.com/v1/tld/org/status" \  -H "Authorization: Bearer <access_token>"

Example response

{ "enabled": true }

Add-on pricing

Covers contact (WHOIS) privacy pricing — currently the only add-on this API exposes.

Get add-on pricing

GET /v1/pricing/add_on

Example response

{  "contact_privacy": {    "usd_price": 4.99,    "foreign_currency_prices": [      { "currency_code": "CAD", "price": 6.49 }    ]  },  "contact_privacy_osrs": 1.50 }

Update add-on pricing

PUT /v1/pricing/add_on

Example request

{  "contact_privacy": {    "usd_price": 4.99,    "foreign_currency_prices": [      { "currency_code": "CAD", "price": 6.49 }    ]  } }

Response: 200 OK


Currencies

Get configured currencies

Returns every currency enabled on your storefront, as an exchange rate against USD.

GET /v1/currencies

Example response

[  {    "code": "CAD",    "descr": "Canadian Dollar",    "symbol": "$",    "is_default": false,    "value_of_1_usd": 1.35,    "active_customers": 214  } ]
FieldDescription
codeISO 4217 currency code
descrHuman-readable name
symbolCurrency symbol
is_defaultWhether this is your default currency
value_of_1_usdExchange rate — units of this currency per 1 USD
active_customersCustomers currently billed in this currency (via auto-renew domains or active subscriptions)

Create or update a currency

There's no separate create call — this same endpoint creates a currency if the code doesn't exist yet, or updates it if it does.

PUT /v1/currency/{code}

Request fields

FieldTypeRequiredDescription
is_defaultbooleanYesWhether this becomes your default currency
value_of_1_usdnumberYesExchange rate — units of this currency per 1 USD

Example cURL

curl -X PUT "https://api.shopco.com/v1/currency/CAD" \  -H "Authorization: Bearer <access_token>" \  -H "Content-Type: application/json" \  -d '{ "is_default": false, "value_of_1_usd": 1.35 }'

Response: 200 OK

Delete a currency

DELETE /v1/currency/{code}

Example cURL

curl -X DELETE "https://api.shopco.com/v1/currency/CAD" \  -H "Authorization: Bearer <access_token>"

Response: 200 OK

Note: the spec doesn't document what happens if you delete your default currency, or one with active customers still billed in it — confirm the actual behavior before publishing.


Default markup

Get default markup

GET /v1/pricing/default_markup

Response: 200 OK — an integer percentage, e.g. 20.

Update default markup

PUT /v1/pricing/default_markup

Example cURL

curl -X PUT "https://api.shopco.com/v1/pricing/default_markup" \  -H "Authorization: Bearer <access_token>" \  -H "Content-Type: application/json" \  -d '20'

Valid range: 0–999. There's no separate "type" — the default markup is always a percentage.

Response: 200 OK


Price rounding

Get price rounding configuration

GET /v1/pricing/rounding

Response: 200 OK — one of rounding_off, rounding_to_dollar, or rounding_to_99.

Update price rounding configuration

PUT /v1/pricing/rounding

Example cURL

curl -X PUT "https://api.shopco.com/v1/pricing/rounding" \  -H "Authorization: Bearer <access_token>" \  -H "Content-Type: application/json" \  -d '"rounding_to_99"'

This is a single storefront-wide setting, not configurable per TLD or currency.

Response: 200 OK


Tax rules

Get all tax rules

GET /v1/tax_rules

Example response

[  {    "id": "b3f1c2d4-5678-4abc-9def-0123456789ab",    "name": "Ontario HST",    "rate": 0.13,    "country": "CA",    "country_name": "Canada",    "state_province": "ON",    "tax_id": "HST-123456"  } ]

An empty array is returned if you haven't configured any tax rules.

Get a tax rule

GET /v1/tax_rule/{tax_rule_id}

tax_rule_id is the UUID returned when the rule was created. Returns null if no rule matches.

Create a tax rule

POST /v1/tax_rule

Request fields

FieldTypeRequiredDescription
namestringYesDisplay name, e.g. Ontario HST
ratenumber (0–1)YesTax rate as a fraction, e.g. 0.13 for 13%
countrystringYes2-letter ISO country code
state_provincestring or nullNoState/province this rule applies to; omit or send null for a country-wide rule
tax_idstring or nullYesYour tax registration ID for this jurisdiction, if any

Example cURL

curl -X POST "https://api.shopco.com/v1/tax_rule" \  -H "Authorization: Bearer <access_token>" \  -H "Content-Type: application/json" \  -d '{    "name": "Ontario HST",    "rate": 0.13,    "country": "CA",    "state_province": "ON",    "tax_id": "HST-123456"  }'

Response: 200 OK

Update a tax rule

PUT /v1/tax_rule/{tax_rule_id}

Same request fields as create — this replaces the rule's fields, not a partial update.

Delete a tax rule

DELETE /v1/tax_rule/{tax_rule_id}

Deleting, updating, or retrieving a tax rule ID that doesn't exist returns an error.

Check tax ID usage

Groups your tax rules by their shared tax_id value and reports how many rules use each one — useful for checking whether a tax registration ID is already attached to other rules before changing or removing it.

GET /v1/tax_rule/tax_ids

Example response

[  { "name": "HST-123456", "used_by": 3 } ]

name here is the tax ID value itself (not a rule name); null represents rules with no tax ID set.


Error responses

Standard validation errors (422) follow FastAPI's usual shape:

{  "detail": [    {      "type": "missing",      "loc": ["body", "rate"],      "msg": "Field required",      "input": {}    }  ] }

Beyond what's called out per endpoint above, any endpoint in this guide can also return:

StatusMeaning
401 UnauthorizedMissing or invalid token
403 ForbiddenAuthenticated, but not authorized for this resource
404 Not FoundResource doesn't exist
409 ConflictResource already exists (on create)
422 Unprocessable EntityRequest failed validation
429 Too Many RequestsRate limit exceeded — check Retry-After header
500 Internal Server ErrorUnexpected failure — contact support, quoting the x-error-id response header

Money values throughout this API are decimals (e.g. 2.33 for $2.33), not integer cents.


Related articles

Questions or issues with the API? Contact OpenSRS Support.

How helpful was this article?

Thanks for your feedback!

Do you still need help? If so please submit a request here.