User Level Tokens
User-level tokens represent a logged-in user or extension.
Types of User-Level Tokens
- User-level token
- User-level agent token
(user token enriched with agent-specific context)
Access Rules
- User-level tokens can ONLY access resources of their own tenant
- Cross-tenant access is not allowed
- Typical endpoints:
/api/v2/contacts/api/v2/stats
- Limited system endpoints may be accessible, for example:
/api/v2/system/version
How to Obtain User-Level Tokens
Login
The first thing that client needs to do is perform login using one of the supported login methods:
- Email/password login
- Two factor auth token login
- SSO token login
Request
POST /api/v2/login
JSON body:
| Name | Type | Description |
|---|---|---|
| type | String | Type of login used. Possible values are: password_auth, tfa_token_auth, sso_token_auth. |
| payload | Object | Object containing login data. Different objects can be sent based on login type. |
In case of TFA login the token is sent as raw token, it should not be hashed.
In case of SSO login you will need to send a hashed token. That token is a base64 encoded string. It is a hash generated with this formula:
hashed_api_token = HMAC(algo: sha256, data: sso_token.timestamp, key: sso_token)
token = Base64(device_uid.timestamp.hashed_api_token)
Payload objects:
- Password
- TFA
- SSO
{
"type": "password_auth",
"payload": {
"email": "user@example.com",
"password": "**********",
"agent_number": "5000",
"agent_pin": "55"
}
}
{
"type": "tfa_token_auth",
"payload": {
"token": "MDFLMlBBQUJNSjI3RkZYSkM5M0tHUVZUUksuMTc1NTI0NDA2My44M...",
"agent_number": "5000",
"agent_pin": "55"
}
}
{
"type": "sso_token_auth",
"payload": {
"token": "MDFLMlBBQUJNSjI3RkZYSkM5M0tHUVZUUksuMTc1NTI0NDA2My44Mz...",
"agent_number": "5000",
"agent_pin": "55"
}
}
Agent number and pin are optional and must be sent only in cases when agent or supervisor edition is used. Agent pin can be empty always (not required field in PBXware UI).
Response
If login is successful you will receive the response in the following format:
{
"access_token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJle...",
"refresh_token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE3N..."
}
Access token is generated in form of a JWT token. That means that it has its expiry time. After the expiration the token needs to be refreshed with refresh token. Clients do not need to check token expiration. To send the access token in your request add it into Authorization header prefixed with Bearer:
Authorization: Bearer {access_token}
Possible errors on login are:
| Description | HTTP Status Code | Status Text |
|---|---|---|
| The request is malformed or contains invalid parameters | 400 | Bad Request |
| The authentication method is not supported | 400 | Bad Request |
| The provided username or password is incorrect | 401 | Unauthorized |
| The provided authentication token is invalid | 401 | Unauthorized |
| Any other unexpected server-side error | 500 | Internal Server Error |
Token Refresh
If on any API request you get unauthorized status code (401) and inside json body you receive code 60000 the first thing you should do is try to refresh your access token. If you do not receive 401 HTTP status code or in body code is not 60000 do not try to refresh token, token is valid!
Request
POST /api/v2/refresh_token
JSON body:
| Name | Type | Description |
|---|---|---|
| refresh_token | String | Your refresh token. |
{
"refresh_token": "MDFLMlBBQUJNSjI3RkZYSkM5M0tHUVZUUksuMTc1NTI0NDA2My44M..."
}
Response
If refresh is successful you will receive the response in the following format (same as when you perform login):
{
"access_token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJle...",
"refresh_token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE3N..."
}
Refresh tokens are rotated on every refresh so keep in mind that you need to change them in your implementation as well.
Same errors apply as on login section.