API Reference
EmbedMyReviews API
Integrate review management into your workflow. Retrieve reviews, manage organisations, send review request invites, and receive real-time webhook notifications.
https://app.your-white-label.com/api/v1Authentication
All API requests require a valid API token. Create tokens from your account settings under API & Webhooks. Include it in the Authorization header of every request.
Authorization Header
Authorization: Bearer your-api-tokenToken permissions
| Permission | Access |
|---|---|
| reviews:read | View reviews |
| request:read | View campaigns |
| request:create | Send review invites |
| organizations:read | View organisations |
| organizations:create | Create organisations |
| organizations:update | Update organisations |
| organizations:delete | Delete organisations |
Rate limiting
60 requests per minute per token. Every response includes rate limit headers.
| Header | Description |
|---|---|
| X-RateLimit-Limit | Maximum requests per window (60) |
| X-RateLimit-Remaining | Remaining requests in current window |
| Retry-After | Seconds to wait before retrying (only on 429) |
Errors
Standard HTTP status codes. Errors return JSON with a message field.
| Code | Status | Description |
|---|---|---|
| 200 | OK | Request succeeded |
| 201 | Created | Resource successfully created |
| 202 | Accepted | Request accepted and queued |
| 401 | Unauthenticated | Missing or invalid API token |
| 403 | Forbidden | Token lacks required permissions |
| 404 | Not Found | Resource does not exist |
| 422 | Validation Error | Request body failed validation |
| 429 | Too Many Requests | Rate limit exceeded |
| 500 | Server Error | Something went wrong on our end |
Pagination
List endpoints return paginated results with 10 items per page. Use the page query parameter to navigate.
{
"data": [...],
"links": {
"first": "https://app.your-white-label.com/api/v1/reviews?page=1",
"last": "https://app.your-white-label.com/api/v1/reviews?page=5",
"prev": null,
"next": "https://app.your-white-label.com/api/v1/reviews?page=2"
},
"meta": {
"current_page": 1,
"from": 1,
"last_page": 5,
"per_page": 10,
"to": 10,
"total": 48
}
}Validation error (422) response
{
"message": "The email field is required when phone is not present.",
"errors": {
"email": [
"The email field is required when phone is not present."
]
}
}/api/v1/reviewsList reviews
Retrieve a paginated list of reviews across all connected sources. Filter by rating, organisation, location, or review source.
Requires reviews:read
Query parameters
| Parameter | Type | Description |
|---|---|---|
| rating | integer | Filter by rating (1-5) |
| organization_id | integer | Filter by organisation |
| location_id | integer | Filter by location |
| source_names[] | array | Filter by source names (e.g. Google, Facebook) |
| page | integer | Page number (default: 1) |
Example request
curl https://app.your-white-label.com/api/v1/reviews?rating=5 \ -H "Authorization: Bearer your-api-token" \ -H "Accept: application/json"
Example response 200 OK
{
"data": [
{
"id": 142,
"organization_id": 1,
"location_id": 3,
"author": "Sarah Johnson",
"date": "2025-12-15T10:30:00.000000Z",
"rating": 5,
"title": null,
"message": "Outstanding service!",
"source": "Google",
"source_logo": "https://example.com/logos/google.svg",
"avatar": "https://...",
"reply": "Thank you Sarah!",
"reply_date": "2025-12-16T09:00:00.000000Z"
}
],
"links": { "first": "...", "last": "...", "prev": null, "next": "..." },
"meta": { "current_page": 1, "from": 1, "last_page": 5, "per_page": 10, "to": 10, "total": 48 }
}/api/v1/organizationsList organisations
Returns a paginated list of all organisations accessible to the authenticated user.
Requires organizations:read
Example request
curl https://app.your-white-label.com/api/v1/organizations \ -H "Authorization: Bearer your-api-token" \ -H "Accept: application/json"
Example response 200 OK
{
"data": [
{
"id": 1,
"name": "Acme Dental Clinic",
"created_at": "2025-01-15T08:30:00.000000Z",
"updated_at": "2025-06-20T14:22:00.000000Z"
}
],
"links": { ... },
"meta": { ... }
}/api/v1/organizationsCreate organisation
Create a new organisation. The name must be unique across your account.
Requires organizations:create
Request body
| Parameter | Type | Description |
|---|---|---|
| name | string | Organisation name (required, max 255 chars, unique) |
| logo | file | Logo image (png, jpg, jpeg, svg, max 250KB) |
Example request
curl -X POST https://app.your-white-label.com/api/v1/organizations \
-H "Authorization: Bearer your-api-token" \
-H "Content-Type: application/json" \
-d '{"name": "Downtown Branch"}'Example response 201 Created
{
"id": 2,
"name": "Downtown Branch",
"created_at": "2025-12-15T10:30:00.000000Z",
"updated_at": "2025-12-15T10:30:00.000000Z"
}/api/v1/organizations/{id}Get organisation
Retrieve a single organisation by its ID.
Requires organizations:read
Example request
curl https://app.your-white-label.com/api/v1/organizations/1 \ -H "Authorization: Bearer your-api-token" \ -H "Accept: application/json"
Example response 200 OK
{
"id": 1,
"name": "Acme Dental Clinic",
"created_at": "2025-01-15T08:30:00.000000Z",
"updated_at": "2025-06-20T14:22:00.000000Z"
}/api/v1/organizations/{id}Update organisation
Update an existing organisation's name or logo.
Requires organizations:update
Request body
| Parameter | Type | Description |
|---|---|---|
| name | string | Organisation name (max 255 chars, unique) |
| logo | file | Logo image (png, jpg, jpeg, svg, max 250KB) |
Example request
curl -X PUT https://app.your-white-label.com/api/v1/organizations/1 \
-H "Authorization: Bearer your-api-token" \
-H "Content-Type: application/json" \
-d '{"name": "Updated Name"}'/api/v1/organizations/{id}Delete organisation
Permanently delete an organisation. This action cannot be undone. You must have at least one remaining organisation.
Requires organizations:delete
Example request
curl -X DELETE https://app.your-white-label.com/api/v1/organizations/1 \ -H "Authorization: Bearer your-api-token" \ -H "Accept: application/json"
Example response 200 OK
{
"message": "Organization deleted successfully."
}/api/v1/request-reviews/campaignsList campaigns
Retrieve your review request campaigns. Use campaign UUIDs to send invites via the Send Invite endpoint.
Requires request:read
Query parameters
| Parameter | Type | Description |
|---|---|---|
| organization_id | integer | Filter campaigns by organisation |
| search | string | Search campaigns by name |
Example request
curl https://app.your-white-label.com/api/v1/request-reviews/campaigns \ -H "Authorization: Bearer your-api-token" \ -H "Accept: application/json"
Example response 200 OK
{
"data": [
{
"id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"name": "Post-Visit Follow Up"
},
{
"id": "f9e8d7c6-b5a4-3210-fedc-ba0987654321",
"name": "Monthly Customer Outreach"
}
],
"links": { ... },
"meta": { ... }
}/api/v1/request-reviews/campaigns/{campaign}/inviteSend review invite
Send a review request invite to a contact via email, SMS, or WhatsApp. This is the primary endpoint for automating review requests from your CRM, POS, or booking system.
Requires request:read + request:create
Path + request body
| Parameter | Type | Description |
|---|---|---|
| campaign | uuid | Campaign UUID (required path parameter, from List Campaigns) |
| string | Contact email. Required when phone is not provided. | |
| phone | string | Phone in E.164 format (e.g. +14275238194). Required when email is not provided. |
| first_name | string | Contact first name (max 255 chars) |
| last_name | string | Contact last name (max 255 chars) |
| send_after_hours | integer | Hours to wait before sending. 0 = send ASAP. null = use campaign default. |
Example request
curl -X POST https://app.your-white-label.com/api/v1/request-reviews/campaigns/{campaign_uuid}/invite \
-H "Authorization: Bearer your-api-token" \
-H "Content-Type: application/json" \
-d '{
"email": "[email protected]",
"first_name": "Sarah",
"send_after_hours": 0
}'Example response 202 Accepted
{
"id": "c7d8e9f0-1234-5678-abcd-ef9876543210",
"message": "Invites sent successfully."
}Important
Duplicate contacts are handled gracefully. If the same contact is submitted again within the campaign's dedup window (default: 14 days), the request returns 202 without error and the contact is silently ignored.
Unsubscribed contacts will not receive new invites, even via the API. Their opt-out is always respected.
Invites respect the campaign's configured send window. Requests outside the window are queued for the next available slot.
Delivery channels (email, SMS, WhatsApp) depend on your campaign step configuration. Providing both email and phone maximises reach.
/api/v1/sourcesList review sources
Retrieve all available review sources (Google, Facebook, Yelp, Trustpilot, etc.) with their capabilities and logos.
Requires Any valid token
Example request
curl https://app.your-white-label.com/api/v1/sources \ -H "Authorization: Bearer your-api-token" \ -H "Accept: application/json"
Example response 200 OK
{
"data": [
{
"id": 1,
"name": "Google",
"url": "https://google.com",
"logo": "https://...",
"available": true,
"can_collect_reviews": true,
"deep_linking_supported": true
}
]
}/api/v1/countriesList countries
Retrieve the full list of supported countries with ISO 3166-1 alpha-2 codes. Useful for populating country selectors.
Requires Any valid token
Example response 200 OK
[
{ "id": "US", "name": "United States" },
{ "id": "GB", "name": "United Kingdom" },
{ "id": "CA", "name": "Canada" },
...
]/api/v1/meCurrent user
Retrieve the authenticated user's basic information. Useful for verifying your API token.
Requires Any valid token
Example response 200 OK
{
"id": 1,
"name": "John Smith",
"email": "[email protected]"
}Agency API
The Agency API lets you manage your customers programmatically — create accounts, switch plans, adjust limits, manage credits, and handle orders. These endpoints use the same authentication but require an agency-level API token generated from the agency account.
Base URL
https://app.your-white-label.com/api/agency/v1Agency tokens have full access across all customer accounts. There are no scoped permissions here, so the token acts as a super admin.
/api/agency/v1/customersCreate customer
Create a new customer account. The customer receives login credentials and is assigned to the specified plan.
Request body
| Parameter | Type | Description |
|---|---|---|
| name | string | Customer name (required) |
| company | string | Organisation/company name (required) |
| string | Login email address (required) | |
| password | string | Password, min 8 characters (required) |
| custom_plan_id | string | Plan ID to assign (required) |
| phone | string | Phone in E.164 format (optional) |
| location_limit | integer | Override plan location limit (optional, min 1) |
| member_limit | integer | Override plan member limit. 0 = unlimited (optional) |
| send_invite | boolean | Email login details to the customer (optional) |
| country | string | ISO 3166-1 alpha-2 code. Required if Stripe Tax is enabled. |
| postal_code | string | Required for US/CA when Stripe Tax is enabled |
Example request
curl -X POST https://app.your-white-label.com/api/agency/v1/customers \
-H "Authorization: Bearer {token}" \
-d name="John Smith" \
-d company="My Clinic" \
-d email="[email protected]" \
-d password="Password123456" \
-d custom_plan_id="2"Example response 200 OK
{
"data": {
"id": 1,
"name": "John Smith",
"email": "[email protected]",
"phone": null,
"language": "en",
"trial_ends_at": null,
"created_at": "2024-09-26T19:57:52.000000Z",
"updated_at": "2024-09-26T19:57:52.000000Z",
"custom_plan": { "id": 2, "name": "Pro" },
"organizations": [{ "id": 1, "name": "My Clinic" }]
}
}/api/agency/v1/customers/{customer}Switch customer plan
Change the customer's assigned plan.
Request body
| Parameter | Type | Description |
|---|---|---|
| custom_plan_id | string | The plan ID to switch to (required) |
Example request
curl -X PUT https://app.your-white-label.com/api/agency/v1/customers/{customer} \
-H "Authorization: Bearer {token}" \
-d custom_plan_id="2"Example response 200 OK
{
"data": {
"id": 1,
"name": "John Smith",
"email": "[email protected]",
"custom_plan": { "id": 2, "name": "Pro" },
"organizations": [{ "id": 1, "name": "My Clinic" }]
}
}/api/agency/v1/customers/{customer}/location-limitUpdate location & member limits
Override the customer's location or member limit independently of their plan defaults. Two separate endpoints.
Request body
| Parameter | Type | Description |
|---|---|---|
| location_limit | integer | PUT .../location-limit: number of locations allowed (min 1) |
| member_limit | integer | PUT .../member-limit: number of team members allowed (0 = unlimited) |
Example request
# Update location limit
curl -X PUT https://app.your-white-label.com/api/agency/v1/customers/{customer}/location-limit \
-H "Authorization: Bearer {token}" \
-d location_limit="5"
# Update member limit
curl -X PUT https://app.your-white-label.com/api/agency/v1/customers/{customer}/member-limit \
-H "Authorization: Bearer {token}" \
-d member_limit="10"Example response 200 OK
{ "message": "Location limit updated successfully." }
// or
{ "message": "Member limit updated successfully." }/api/agency/v1/customers/{customer}/add-creditsAdd credits
Add email or SMS credits to a customer's account. Credits can optionally expire.
Request body
| Parameter | Type | Description |
|---|---|---|
| type | string | Credit type: "email" or "sms" (required) |
| credits | integer | Number of credits to add, min 1 (required) |
| expires_at | date | Expiry date in Y-m-d format (optional) |
| notes | string | Note visible to the customer (optional) |
Example request
curl -X POST https://app.your-white-label.com/api/agency/v1/customers/{customer}/add-credits \
-H "Authorization: Bearer {token}" \
-d type="email" \
-d credits="1000"Example response 200 OK
{
"message": "Credits added successfully.",
"balance": 250
}/api/agency/v1/customers/{customer}/pausePause & resume subscription
Pause or resume a customer's subscription. Only available when the plan is not linked to Stripe (for Stripe-managed subscriptions, use Stripe's native pause).
Example request
# Pause subscription
curl -X PUT https://app.your-white-label.com/api/agency/v1/customers/{customer}/pause \
-H "Authorization: Bearer {token}"
# Resume subscription
curl -X PUT https://app.your-white-label.com/api/agency/v1/customers/{customer}/resume \
-H "Authorization: Bearer {token}"Example response 200 OK
{ "message": "Subscription has been paused." }
// or
{ "message": "Subscription has been resumed." }/api/agency/v1/customers/{customer}Delete customer
Permanently delete a customer account.
Example request
curl -X DELETE https://app.your-white-label.com/api/agency/v1/customers/{customer} \
-H "Authorization: Bearer {token}"Example response 200 OK
{ "message": "Customer deleted successfully." }/api/agency/v1/customersList all customers
Retrieve a paginated list of all your customers with their plans and organisations.
Parameters
| Parameter | Type | Description |
|---|---|---|
| search | string | Search by name or email (optional) |
Example request
curl https://app.your-white-label.com/api/agency/v1/customers \
-H "Authorization: Bearer {token}"Example response 200 OK
{
"data": [
{
"id": 1,
"name": "John Smith",
"email": "[email protected]",
"phone": null,
"language": "en",
"trial_ends_at": "2023-08-24T16:57:57.000000Z",
"created_at": "2023-07-25T16:57:57.000000Z",
"updated_at": "2023-08-04T15:01:11.000000Z",
"custom_plan": { "id": 2, "name": "Pro" },
"organizations": [{ "id": 2, "name": "My Clinic" }]
}
],
"links": { ... },
"meta": { "current_page": 1, "from": 1, "per_page": 10, "to": 10 }
}/api/agency/v1/custom-plansList all plans
Retrieve all custom plans you've created. Use the plan ID when creating customers or switching plans.
Example request
curl https://app.your-white-label.com/api/agency/v1/custom-plans \
-H "Authorization: Bearer {token}"Example response 200 OK
{
"data": [
{
"id": 1,
"stripe_monthly_id": "",
"stripe_yearly_id": "",
"name": "Basic",
"is_default": false,
"is_hidden": false,
"is_free": true,
"updated_at": "2024-09-26T10:19:58.000000Z",
"created_at": "2023-07-25T15:14:02.000000Z"
}
]
}/api/agency/v1/ordersOrders (NFC products)
Manage NFC product orders. List all orders, mark as shipped (with optional tracking URL), complete, or cancel.
Example request
# List orders
curl https://app.your-white-label.com/api/agency/v1/orders \
-H "Authorization: Bearer {token}"
# Ship order (with optional tracking URL)
curl -X PUT https://app.your-white-label.com/api/agency/v1/orders/{order}/ship \
-H "Authorization: Bearer {token}" \
-d tracking_url="https://tracking.example.com/123"
# Complete order
curl -X PUT https://app.your-white-label.com/api/agency/v1/orders/{order}/complete \
-H "Authorization: Bearer {token}"
# Cancel order
curl -X PUT https://app.your-white-label.com/api/agency/v1/orders/{order}/cancel \
-H "Authorization: Bearer {token}"Example response 200 OK
{
"data": [
{
"id": "27d2ba02-...",
"order_number": "HUFTMX-1733678942",
"email": "[email protected]",
"total": 49.99,
"currency": "usd",
"status": "completed",
"shipping": {
"name": "John Smith",
"address": "49 Featherstone Street",
"city": "London",
"country": "GB",
"tracking_url": null
},
"items": [
{
"product_name": "Google Review Card",
"quantity": 1,
"unit_price": 29.99,
"nfc_urls": ["https://your-domain.com/nfc/..."]
}
]
}
]
}Webhooks
Receive real-time HTTP notifications when events occur. Configure your webhook URL in Settings → API & Webhooks.
| Property | Value |
|---|---|
| HTTP Method | POST |
| Content-Type | application/json |
| User-Agent | ReviewManagement/V1 |
| Retry Policy | Up to 10 retries over 5 minutes with exponential backoff |
| Timeout | 30 seconds per attempt |
Events
| Event | Triggered when |
|---|---|
| review-created | A new review is received from any connected source |
| review-updated | An existing review is modified (reply added, rating changed) |
| organization-created | A new organisation is created |
| organization-updated | An organisation's details are modified |
| organization-deleted | An organisation is deleted |
| location-created | A new location is added |
| location-updated | A location's details are modified |
| location-deleted | A location is removed |
Example payload (review-created)
{
"webhook_event": "review-created",
"id": 142,
"organization_id": 1,
"location_id": 3,
"source_name": "google",
"identifier": "AbcXyz123",
"avatar": "https://lh3.googleusercontent.com/a/photo.jpg",
"author": "Sarah Johnson",
"rating": 5,
"original_rating": 5,
"title": null,
"message": "Outstanding service! The team went above and beyond.",
"url": "https://maps.google.com/review/...",
"verified": true,
"replied": false,
"reply_message": null,
"reply_url": null,
"hidden": false,
"reply_published_on": null,
"published_on": "2025-12-15T10:30:00+00:00",
"review_updated_on": null,
"updated_at": "2025-12-15T10:35:00+00:00",
"created_at": "2025-12-15T10:35:00+00:00",
"meta": {}
}