Get a brand's customer portal
The portal.brand.get operation: GET /api/v1/public/{brandSlug}/portal in the REST API and the portal_brand_get tool in the MCP server.
GET
/api/v1/public/{brandSlug}/portalReturns what a brand's customer portal shows before sign-in: the brand's name, logo, color and support links,
the seller (legal name, address and VAT ID), and the mode the portal's sign-in works in (livemode: test mode
for a brand that is still test-only, live mode once it is live).
Public: no API key needed. Draft and suspended brands have no portal (resource_not_found).
At a glance
- REST:
GET /api/v1/public/{brandSlug}/portal - MCP tool:
portal_brand_get - Operation ID:
portal.brand.get - Scope: Brand
- Permission:
portal:read - Risk tier:
read - Dry run: Not supported
- Idempotency: Not needed (read only)
- Modes: Test and live
- Authentication: None (a public endpoint, rate-limited per IP address)
- Since: M9
Request
Path parameters
| Field | Type | Description |
|---|---|---|
brandSlug | string | The brand's slug, as in /portal/{brandSlug}. |
Query parameters
This operation takes no query parameters.
Response
200 OK with a JSON object:
| Field | Type | Description |
|---|---|---|
object | "portal_brand" | |
slug | string | |
name | string | |
livemode | boolean | The mode the portal's sign-in page works in: test for a test-only brand. |
logoUrl | string or null | |
primaryColor | string or null | |
supportEmail | string or null | |
supportUrl | string or null | |
termsUrl | string or null | |
privacyUrl | string or null | |
seller | object | The seller: “Sold by {legal name}, {address}, {VAT ID}” (spec §40.2). |
seller.legalName | string | |
seller.address | string | |
seller.taxId | string | |
locales | array of string | The brand's languages, its default first (checkoutSettings.locales): the portal's fallback. |
Examples
Genno's portal (test-only brand)
HTTP
GET /api/v1/public/genno/portal
Response (200):
JSON
{
"object": "portal_brand",
"slug": "genno",
"name": "Genno",
"livemode": false,
"logoUrl": null,
"primaryColor": "#5b3df5",
"supportEmail": "help@genno.example",
"supportUrl": null,
"termsUrl": "https://genno.example/terms",
"privacyUrl": "https://genno.example/privacy",
"seller": {
"legalName": "Etna Labs AG",
"address": "Dammstrasse 16, 6300 Zug, Switzerland",
"taxId": "CHE-181.927.786 MWST"
},
"locales": ["en", "hr"]
}
Errors
| Code | HTTP status | When | What to do |
|---|---|---|---|
validation_failed | 400 | brandSlug isn't a slug. | Fix the fields listed in details.issues and send the request again. |
resource_not_found | 404 | No brand with this slug has a customer portal (draft and suspended brands have none). | Check the ID and that your credentials are scoped to the right organization, entity, brand and mode. |
rate_limited | 429 | Too many requests from this address or client IP; wait retry_after_ms. | Wait for retry_after_ms and retry with backoff. |
It can also return these common errors: api_version_unsupported, scope_required, dry_run_not_supported, internal_error.