Summary and recommendation
Bandwidth exposes a Dashboard REST API at `https://dashboard.bandwidth.com/api/` supporting full user lifecycle operations: list, get, create, update, and delete. Authentication uses HTTP Basic Auth scoped to an `accountId` - there is no global API key model. Credentials are retrieved from Account > My Profile in the Dashboard.
A critical default behavior to handle immediately: the API returns XML unless you explicitly set `Accept: application/json` and `Content-Type: application/json` on every request. This is not flagged prominently in the public developer portal and will break JSON-parsing integrations silently.
For teams managing Bandwidth alongside a broader identity stack, Stitchflow connects via an MCP server with ~100 deep IT/identity integrations, enabling automated provisioning workflows against the Dashboard API without building custom middleware from scratch.
API quick reference
| Has user API | Yes |
| Auth method | HTTP Basic Authentication (username:password or token) for Dashboard/Account API; API credentials (accountId + username + password) for most REST calls |
| Base URL | Official docs |
| SCIM available | No |
| SCIM plan required | Enterprise |
Authentication
Auth method: HTTP Basic Authentication (username:password or token) for Dashboard/Account API; API credentials (accountId + username + password) for most REST calls
Setup steps
- Log in to the Bandwidth Dashboard at dashboard.bandwidth.com.
- Navigate to Account > My Profile to retrieve your API credentials (username and API token/password).
- Use your accountId, API username, and API password as HTTP Basic Auth credentials (Base64-encoded) in the Authorization header.
- For voice/messaging APIs, use the application credentials (accountId, username, password) provided in the dashboard.
User object / data model
| Field | Type | Description | On create | On update | Notes |
|---|---|---|---|---|---|
| userId | string | Unique identifier for the user | system-generated | immutable | Assigned by Bandwidth |
| username | string | Login username for the user | required | optional | Must be unique within the account |
| firstName | string | User's first name | required | optional | |
| lastName | string | User's last name | required | optional | |
| string | User's email address | required | optional | Used for notifications and login | |
| roles | array | List of roles assigned to the user | optional | optional | Controls dashboard permissions |
| accountId | string | The account this user belongs to | required | immutable | Top-level account identifier |
| password | string | User password (write-only) | required | optional | Never returned in responses |
| enabled | boolean | Whether the user account is active | optional | optional | Defaults to true |
Core endpoints
List Users
- Method: GET
- URL:
https://dashboard.bandwidth.com/api/accounts/{accountId}/users - Watch out for: Response XML or JSON format may vary; the API historically returns XML by default. Set Accept: application/json if JSON is needed.
Request example
GET /api/accounts/12345/users
Authorization: Basic {base64(user:pass)}
Response example
{
"Users": [
{"UserId":"u1","Username":"jdoe","FirstName":"John","LastName":"Doe","Email":"jdoe@example.com"}
]
}
Get User
- Method: GET
- URL:
https://dashboard.bandwidth.com/api/accounts/{accountId}/users/{userId} - Watch out for: userId must be the internal Bandwidth user ID, not the username.
Request example
GET /api/accounts/12345/users/u1
Authorization: Basic {base64(user:pass)}
Response example
{
"UserId":"u1",
"Username":"jdoe",
"FirstName":"John",
"LastName":"Doe",
"Email":"jdoe@example.com"
}
Create User
- Method: POST
- URL:
https://dashboard.bandwidth.com/api/accounts/{accountId}/users - Watch out for: Password complexity requirements are enforced but not publicly documented. Weak passwords return a 400 error.
Request example
POST /api/accounts/12345/users
Content-Type: application/json
{"Username":"jdoe","FirstName":"John","LastName":"Doe","Email":"jdoe@example.com","Password":"Secret123!"}
Response example
{
"UserId":"u2",
"Username":"jdoe",
"FirstName":"John",
"LastName":"Doe"
}
Update User
- Method: PUT
- URL:
https://dashboard.bandwidth.com/api/accounts/{accountId}/users/{userId} - Watch out for: Full PUT semantics may apply; omitting fields could reset them. Verify with Bandwidth support.
Request example
PUT /api/accounts/12345/users/u1
Content-Type: application/json
{"FirstName":"Jane","Email":"jane@example.com"}
Response example
{
"UserId":"u1",
"Username":"jdoe",
"FirstName":"Jane",
"Email":"jane@example.com"
}
Delete User
- Method: DELETE
- URL:
https://dashboard.bandwidth.com/api/accounts/{accountId}/users/{userId} - Watch out for: Deleting a user is irreversible. Ensure the user has no active sub-accounts or resources assigned.
Request example
DELETE /api/accounts/12345/users/u1
Authorization: Basic {base64(user:pass)}
Response example
HTTP 200 OK
{}
List Roles
- Method: GET
- URL:
https://dashboard.bandwidth.com/api/accounts/{accountId}/roles - Watch out for: Available roles are account-specific and may differ from defaults.
Request example
GET /api/accounts/12345/roles
Authorization: Basic {base64(user:pass)}
Response example
{
"Roles": [
{"RoleId":"r1","RoleName":"Admin"},
{"RoleId":"r2","RoleName":"ReadOnly"}
]
}
Rate limits, pagination, and events
Rate limits: Bandwidth does not publicly document specific rate limit tiers for the Dashboard/Account Management API. Voice and messaging APIs have per-account throughput limits negotiated at contract time.
Rate-limit headers: No
Retry-After header: No
Rate-limit notes: Rate limits are not publicly specified. Contact Bandwidth support for account-specific limits. HTTP 429 is returned when limits are exceeded.
Pagination method: none
Default page size: 0
Max page size: 0
Pagination pointer: Not documented
Webhooks available: No
Webhook notes: Bandwidth does not offer webhooks for user-management events (user created, updated, deleted). Webhooks are available for voice and messaging events (call status, message delivery) but not for account/user lifecycle events.
Alternative event strategy: Poll the List Users endpoint periodically to detect changes, or use SSO/SCIM provisioning flows for automated lifecycle management.
SCIM API status
- SCIM available: No
- SCIM version: Not documented
- Plan required: Enterprise
- Endpoint: Not documented
Limitations:
- SCIM provisioning is not natively supported by Bandwidth as of the latest available documentation.
- SSO is supported via SAML 2.0 with Okta, Microsoft Entra ID, and OneLogin, but automated SCIM provisioning is not available.
- User provisioning must be done manually via the Dashboard UI or the Dashboard REST API.
Common scenarios
Provisioning a new user requires a POST to /api/accounts/{accountId}/users with username, firstName, lastName, email, and password.
Password complexity is enforced server-side with no public documentation of the rules - use 12+ character mixed-case passwords with numbers and symbols to avoid opaque 400 errors. Capture the returned userId immediately; subsequent role assignments and deprovisioning calls require it, not the username.
Deprovisioning has no disable or suspend endpoint documented publicly. The only API-supported offboarding path is a permanent DELETE to /api/accounts/{accountId}/users/{userId}. Verify removal with a follow-up GET confirming a 404 before closing the offboarding ticket.
For IdP sync without native SCIM (e.g., Okta), configure SAML 2.0 SSO in the Dashboard, then bridge Okta lifecycle events to Bandwidth API calls via custom middleware - Okta Workflows, a Lambda, or equivalent. Map email, firstName, and lastName from Okta attributes to Bandwidth user fields. On Okta deactivation, trigger the DELETE endpoint; there is no softer deactivation state available via API.
Provision a new user to a Bandwidth account
- Authenticate using HTTP Basic Auth with your accountId credentials.
- POST to /api/accounts/{accountId}/users with the new user's username, firstName, lastName, email, and password.
- Capture the returned userId for future operations.
- Optionally assign roles by updating the user with the desired roleIds.
Watch out for: Password complexity is enforced server-side without public documentation of requirements. Test with a strong password (12+ chars, mixed case, numbers, symbols).
Deprovision a user when they leave the organization
- GET /api/accounts/{accountId}/users to find the userId by username or email.
- Confirm the user has no critical resources assigned.
- DELETE /api/accounts/{accountId}/users/{userId} to remove the user.
- Verify removal by attempting GET /api/accounts/{accountId}/users/{userId} and confirming a 404 response.
Watch out for: Deletion is permanent. There is no disable/suspend endpoint documented publicly; deletion is the only deprovisioning option via API.
Sync users from an IdP (Okta) without SCIM
- Configure SAML 2.0 SSO in Bandwidth Dashboard with Okta as the IdP.
- For provisioning, use the Bandwidth Dashboard REST API to create users programmatically via a custom Okta workflow or lifecycle hook.
- Map Okta user attributes (email, firstName, lastName) to Bandwidth user fields in your integration script.
- On Okta user deactivation, trigger a DELETE call to /api/accounts/{accountId}/users/{userId} via your integration.
Watch out for: Native SCIM is not supported. This requires a custom middleware or workflow automation (e.g., Okta Workflows, Zapier, or a custom Lambda) to bridge Okta lifecycle events to Bandwidth API calls.
Why building this yourself is a trap
SCIM is not natively supported by Bandwidth. SSO via SAML 2.0 is available with Okta, Entra ID, and OneLogin, but it does not include automated provisioning - every user lifecycle event requires a direct API call or manual Dashboard action.
Rate limits are not publicly documented and are negotiated per account. Unexpected HTTP 429 responses should be handled with exponential backoff; there are no Retry-After or rate-limit headers returned. The PUT update endpoint may apply full-replacement semantics - omitting fields could reset them, and Bandwidth support confirmation is advised before running bulk updates in production.
The user management endpoints are not prominently surfaced in the public developer portal, and some operations may require support confirmation to validate behavior. Build against this API with the assumption that undocumented edge cases exist, and instrument your integration to log full request/response payloads during initial rollout.
Automate Bandwidth workflows without one-off scripts
Stitchflow builds and maintains end-to-end IT automation across your SaaS stack, including apps without APIs. Built for exactly how your company works, with human approvals where they matter.