Skip to main content
MaestroQA API

Articles for Admin to help get started with MaestroQA API

Matt avatar
Written by Matt
Updated today

Overview

The MaestroQA API allows users to access and interact with their quality assurance data programmatically. By using the API, users can automate repetitive tasks, integrate MaestroQA with other tools, and build custom applications that leverage their QA data. In this article, we'll explore the main features of the MaestroQA API, show examples of how it can be used, and provide guidance on how to get started.

Whether you're a seasoned developer or new to APIs, this article will help you understand how to unlock the full potential of MaestroQA by using its API.

Table of Contents


Authentication

In order to make requests to the Maestro QA API, you must attach a valid API token to your request.

Obtaining an API Token

API tokens can be generated in the MaestroQA dashboard on the Other Settings page. Within "Other Settings", scroll down to the API Tokens section and click "Create New Token".

By default, API Tokens expire every 90 days for security purposes. This expiration can be turned off, or tokens can be deactivated manually.

Authenticating Requests

An API token must be provided for all requests. The token should be passed in the request's headers, in the format:

'apitoken': 'YOUR_API_TOKEN'

Example (Python)

import requests

headers = {
'Content-Type': 'application/json',
'apitoken': 'YOUR_API_TOKEN'
}

response = requests.get(url, headers=headers)

Certain endpoints allow tokens to be passed in the request body (noted in the endpoint's documentation); this is supported for backward compatibility only and is subject to change.

__________________________________________________________________

Formats

1. All dates should be UTC offset datetime strings, formatted according to the extended ISO 8601 format (reference)

[YYYY]-[MM]-[DD]T[HH]:[MM]:[SS]Z

ex. 2017-12-13T05:00:00Z

2. Each endpoint’s request parameters and response content should be JSON-encoded

Endpoints

The * symbol is used to denote required parameters

If a parameter is optional, it may be omitted from the request parameters. If an optional parameter is included, it must contain a valid value.

Request A “Raw” Export

Raw exports are the equivalent to the Raw CSV export in the MaestroQA dashboard. The export will include grades that were last updated between the specified start date and end date.

Raw exports generate a zip file containing a CSV for each level of rubric scores:

  • total rubric scores

  • section scores

  • individual answer scores

  • annotations

  • CSAT

Definition

POST https://app.maestroqa.com/api/v1/request-raw-export

Body Parameters

Name

Type

Description

startDate*

string (see formats)

Include grades that were updated after this date
(required)

endDate*

string (see formats)

Include grades that were updated before this date
(required)

name

string

Name for the export. Defaults to a randomly generated name
(optional)

singleFileExport

enum

(individual_answers, section_scores, total_scores, annotations, csat)

Specify a single csv file to export instead of the default zip file with all csvs

(optional)

includeCalibrations

enum

(all, none, only)

Specify whether calibration scores should be included in the export.

  • "none": (default) - don't include calibration scores

  • "only": only include calibration scores

  • "all": include all scores, regardless of type

(optional)

includeGraderQA

boolean

Specify whether grader QA benchmark scores should be included in the export. Default is false

(optional)

includeDeleted

boolean

Specify whether deleted answers should be included in the export. Default is false (optional)

apiToken

string

See authentication
(optional) - token may be passed in request body or in request headers

Response

The ID of the export that was requested - used to track the export's status and retrieve its results.

Name

Type

Description

exportId

string

ID of the export that was requested

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/request-raw-export'

payload = {
'startDate': '2018-08-13T00:00:00Z',
'endDate': '2018-08-19T00:00:00Z',
'name': 'Weekly Maestro Grades Export'
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.post(url, json=payload, headers=headers)

Example Response

{ 'exportId': 'id_1234' }


Retrieve the results of an export

After an export has been requested, check its status and fetch the URL from which to download the export’s results.

Definition

GET https://app.maestroqa.com/api/v1/get-export-data

Body Parameters

Name

Type

Description

exportId*

string

The ID of the export whose results should be returned
(required)

apiToken

string

See authentication
(optional) - token may be passed in request body or in request headers

Response

Status and result data for the requested export

Name

Type

Description

status

enum

(requested, in_progress, complete, errored)

The status of the export

dataUrl

string

If status is "complete" and there is data to download, contains the URL to download the export. Otherwise, contains an empty string.

Note: if there was no matching data for the parameters requested (ex. if you request dates in the future), the dataUrl field will be empty, even when the status is 'complete' as there is nothing to download.

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/get-export-data'

payload = {
'exportId': 'THE_EXPORT_ID'
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.get(url, json=payload, headers=headers)

Example Response

{
'status': 'complete',
'dataUrl': 'https://subdomain.s3.amazonaws.com/path/to/file'
}

Here is a Data Dictionary for the files contained within the resulting export.


Request an “agent groups” export

An “agent groups” export is the equivalent to the Agent Groups export in the MaestroQA App. This will export all the agent groups and group membership.

Definition

POST https://app.maestroqa.com/api/v1/request-groups-export

Body Parameters

Name

Type

Description

name

string

Name for the export. Defaults to a randomly generated name
(optional)

includeUnavailable

boolean

Whether to include all agents, or just those currently marked “available”. Default is false.

(optional)

apiToken

string

See authentication
(optional) - token may be passed in request body or in request headers

Response

The ID of the export that was requested - used to track the export's status and retrieve its results.

Name

Type

Description

exportId

string

ID of the export that was requested

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/request-groups-export'

payload = {
'name': 'Maestro Agent Groups Export',
'includeUnavailable': False
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.post(url, json=payload, headers=headers)

Example Response

{ 'exportId': 'id_1234' }


Request an “audit logs” export

An “audit log” export is the equivalent to the Activity Logs export in the MaestroQA App. This will export all the user activity in your account during the specified date range. See "What Can I Track in the Activity Log" for details on what is tracked in the activity log.

Definition

POST https://app.maestroqa.com/api/v1/request-audit-log-export

Body Parameters

Name

Type

Description

startDate*

string (see formats)

Include logs that were created after this date
(required)

endDate*

string (see formats)

Include logs that were created before this date
(required)

name

string

Name for the export. Defaults to a randomly generated name
(optional)

apiToken

string

See authentication
(optional) - token may be passed in request body or in request headers

Response

The ID of the export that was requested - used to track the export's status and retrieve its results.

Name

Type

Description

exportId

string

ID of the export that was requested

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/request-audit-log-export'

payload = {
'startDate': '2018-08-13T00:00:00Z',
'endDate': '2018-08-19T00:00:00Z',
'name': 'Maestro Activity Log Export',
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.post(url, json=payload, headers=headers)

Example Response

{ 'exportId': 'id_1234' }


Create a Ticket

Create a new Ticket in your MaestroQA account.

Definition

POST https://app.maestroqa.com/api/v1/tickets

Body Parameters

Name

Type

Description

ticket_id*

string

A unique identifier for the ticket.

(required)

Note: this id must be unique - if the id is in use by any other ticket in your account, the request will fail with a 409 Conflict error

type*

string

The ticket type/source from your external support system

(required)

subject*

string

The ticket's subject

(required)

agents*

array[string]

A list of the IDs or emails of agents associated with the ticket

(required)

See Guide to User Roles for information about Agent IDs

link*

string

A link to the ticket in your external resource

(required)

body

string

Text content block of the ticket. (recommended* - see Create a Ticket Comment for sending threaded text based content and Create an Attachment for sending media and other file type attachments)

tags

string

The ticket's tags, formatted as a comma-separated string

status

string

The ticket's status

(ex: "Closed")

csat_score

number

The CSAT score for the ticket

first_seen

date string (see formats)

The date the ticket was created

Defaults to the current date

last_seen

date string (see formats)

The date of the last activity on the ticket

Defaults to the current date

attributes

object

Custom attributes for the ticket

Note: these attributes must already exist in your MaestroQA account. The values passed for each key will be validated against the attribute's expected value type (ex: string, boolean, etc.). Unrecognized attributes will be ignored.

Response

The ticket that was created

Name

Type

Description

ticket_id

string

A unique identifier for the ticket.

type

string

The ticket type/source from your external support system

subject

string

The ticket's subject

agents

array[string]

A list of the IDs of agents associated with the ticket

link

string

A link to the ticket in your external resource

body

string

The text content of the ticket

tags

string

The ticket's tags, formatted as a comma-separated string

status

string

The ticket's status

csat_score

number

The CSAT score for the ticket

first_seen

date string (see formats)

The date the ticket was created

last_seen

date string (see formats)

The date of the last activity on the ticket

attributes

object

The ticket's custom attributes

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/tickets'

payload = {
'ticket_id': 'unique_ticket_id',
'type': 'custom helpdesk',
'subject': 'New ticket',
'link': 'http://www.mynewticket.com',
'body': 'The text content of this ticket',
'status': 'open',
'agents': ['this_agent_id'],
'tags': 'login,support,escalated',
'csat_score': 5,
'first_seen': '2022-02-02T00:00:00.000Z',
'last_seen': '2022-03-07T00:00:00.000Z',
'attributes': {
'public_comment_count': 5,
'group': 'Support',
'first_resolution_time_total_minutes': 1023
}
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.post(url, json=payload, headers=headers)

Example Response

{
'ticket_id': 'unique_ticket_id',
'type': 'custom helpdesk',
'subject': 'New ticket',
'link': 'http://www.mynewticket.com',
'body': 'The text content of this ticket',
'status': 'open',
'agents': ['this_agent_id'],
'tags': 'login,support,escalated',
'csat_score': 5,
'first_seen': '2022-02-02T00:00:00.000Z',
'last_seen': '2022-03-07T00:00:00.000Z',
'attributes': {
'public_comment_count': 5,
'group': 'Support',
'first_resolution_time_total_minutes': 1023
}
}


Update a Ticket

Update an existing Ticket in your MaestroQA account.

Note: tickets fields synced from helpdesk integrations cannot be manually updated, but you can update/set custom fields

Definition

PATCH https://app.maestroqa.com/api/v1/tickets/:ticket_id

Path Parameters

Name

Type

Description

ticket_id*

string

The unique identifier for the ticket

(required)

Body Parameters

Name

Type

Description

type

string

The ticket type/source from your external support system

subject

string

The ticket's subject

agents

array[string]

A list of the IDs or emails of agents associated with the ticket

See Guide to User Roles for information about Agent IDs

link

string

A link to the ticket in your external resource

body

string

The text content of the ticket

tags

string

The ticket's tags, formatted as a comma-separated string

status

string

The ticket's status

(ex: "Closed")

csat_score

number

The CSAT score for the ticket

first_seen

date string (see formats)

The date the ticket was created

last_seen

date string (see formats)

The date of the last activity on the ticket

attributes

object

Custom attributes for the ticket

Note: these attributes must already exist in your MaestroQA account. The values passed for each key will be validated against the attribute's expected value type (ex: string, boolean, etc.). Unrecognized attributes will be ignored.

Response

The updated ticket

Name

Type

Description

ticket_id

string

A unique identifier for the ticket.

type

string

The ticket type/source from your external support system

subject

string

The ticket's subject

agents

array[string]

A list of the IDs of agents associated with the ticket

link

string

A link to the ticket in your external resource

body

string

The text content of the ticket

tags

string

The ticket's tags, formatted as a comma-separated string

status

string

The ticket's status

csat_score

number

The CSAT score for the ticket

first_seen

date string (see formats)

The date the ticket was created

last_seen

date string (see formats)

The date of the last activity on the ticket

attributes

object

The ticket's custom attributes

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/tickets/unique_ticket_id'

payload = {
'subject': 'Updated subject!',
'status': 'closed',
'last_seen': '2022-03-15T00:00:00.000Z'
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.patch(url, json=payload, headers=headers)

Example Response

{
'_id': 'unique_maestro_id_for_ticket',
'ticket_id': 'unique_ticket_id',
'type': 'custom helpdesk',
'subject': 'Updated subject!',
'link': 'http://www.mynewticket.com',
'body': 'The text content of this ticket',
'status': 'closed',
'agents': ['this_agent_id'],
'tags': 'login,support,escalated',
'csat_score': 5,
'first_seen': '2022-02-02T00:00:00.000Z',
'last_seen': '2022-03-15T00:00:00.000Z'
}


Delete a Ticket

Delete an existing Ticket in your MaestroQA account.

Note: tickets synced from helpdesk integrations cannot be manually deleted

Definition

DELETE https://app.maestroqa.com/api/v1/tickets/:ticket_id

Path Parameters

Name

Type

Description

ticket_id*

string

The unique identifier for the ticket

(required)

Response

N/A - successful delete requests will receive a 200 OK response

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/tickets/unique_ticket_id'

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.delete(url, headers=headers)


Get a Ticket

Get basic information about an existing ticket.

Note: only basic ticket data is available for security/privacy considerations. Ticket attributes will only return for manually created tickets and will otherwise be redacted.

Definition

GET https://app.maestroqa.com/api/v1/tickets/:ticket_id

Path Parameters

Name

Type

Description

ticket_id*

string

The unique identifier for the ticket

(required)

Response

The updated ticket

Name

Type

Description

ticket_id

string

A unique identifier for the ticket.

type

string

The ticket type/source from your external support system

subject

string

The ticket's subject

agents

array[string]

A list of the IDs of agents associated with the ticket

link

string

A link to the ticket in your external resource

body

string

The text content of the ticket

tags

string

The ticket's tags, formatted as a comma-separated string

status

string

The ticket's status

csat_score

number

The CSAT score for the ticket

first_seen

date string (see formats)

The date the ticket was created

last_seen

date string (see formats)

The date of the last activity on the ticket

createdAt

date string (see formats)

The date the ticket was created

updatedAt

date string (see formats)

The date the ticket was last updated

source

string

The source designated for the ticket

attributes

object

The ticket's custom attributes

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/tickets/unique_ticket_id'

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.get(url, headers=headers)

Example Response

{
"id": "unique_maestro_id_for_ticket",
"ticket_id": "unique_ticket_id",
"type": "custom helpdesk",
"subject": "Ticket Subject!",
"agents": [
"1"
],
"link": "http://www.mynewticket.com",
"body": "The text content of this ticket",
"tags": "tag1",
"status": "closed",
"csat_score": "10",
"first_seen": "2024-11-06T20:46:57.934Z",
"last_seen": "2024-11-06T20:46:57.934Z",
"createdAt": "2024-11-06T20:46:58.831Z",
"updatedAt": "2024-11-06T20:49:04.954Z",
"source": "custom",
"attributes": {
"public_comment_count": 5,
"recontact": true,
"group": "Support",
"first_resolution_time_total_minutes": 10520,
"full_resolution_time_total_minutes": 100000
}
}


Create a Ticket Comment

Create a comment for a specific ticket. Comments can represent dialogue from customers or agents.

Definition

POST https://app.maestroqa.com/api/v1/comments

Body Parameters

Name

Type

Required

Description

body

string

Yes

The content of the comment

ticket_id

string

Yes

The unique identifier of the ticket to which the comment is being added

author_id

string

No

The identifier of the author (agent or customer) of the comment

role

enum

(customer, agent)

No

The role of the comment author (agent or customer)

channel

string

No

The communication channel through which the comment was made (e.g. chat)

public

boolean

No

Whether or not the comment was public. Defaults to true.

time

date string (see formats)

No

The timestamp of when the comment was made. Defaults to the current time

Response

The comment that was created

Name

Type

Description

id

string

The unique identifier for the comment

body

string

The content of the comment

ticket_id

string

The identifier of the ticket associated with the comment

author_id

string

The identifier of the author

role

enum

(agent, customer)

The role of the comment author

channel

string

The channel used for the comment

public

boolean

Whether the comment is public

time

date string

The timestamp of the comment

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/comments'

payload = {
'ticket_id': '427406478143',
'channel': 'chat',
'time': '2023-11-03T16:38:53.508Z',
'body': 'Hi, can I get some help?',
'role': 'customer',
'author_id': 'customer_12345',
'public': True
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.post(url, json=payload, headers=headers)

Example Response

{
"body": "Hi, can I get some help?",
"author_id": "customer_12345",
"role": "customer",
"channel": "chat",
"public": true,
"time": "2023-11-03T16:38:53.508Z",
"ticket_id": "427406478143",
"id": "16906fb5ce9d57646fa38362_427406478143_W7OU22JH4Q"
}


Create Many Ticket Comments

Create a batch of comments for one or more tickets. Comments can represent dialogue from customers or agents.

Definition

POST https://app.maestroqa.com/api/v1/comments-batch

Body Parameters

Name

Type

Required

Description

batch

array

Yes

Array of comment objects (see structure of a "comment" object from Create a Ticket Comment request arguments)

*Note: there is a maximum of 500 comments per batch

Response

The comments that were created

Name

Type

Description

results

array

Array of created comment objects (see structure of a "comment" response from Create a Ticket Comment response documentation)

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/comments-batch'

payload = {
batch: [
{
'ticket_id': '427406478143',
'channel': 'chat',
'time': '2023-11-03T16:38:53.508Z',
'body': 'Hi, can I get some help?',
'role': 'customer',
'author_id': 'customer_12345',
'public': True
},
{
'ticket_id': '513309837',
'channel': 'email',
'time': '2024-11-03T16:38:53.508Z',
'body': 'I have questions that need answering',
'role': 'customer',
'author_id': 'customer_abcdef',
'public': True
}
]
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.post(url, json=payload, headers=headers)

Example Response

{
results: [
{
"body": "Hi, can I get some help?",
"author_id": "customer_12345",
"role": "customer",
"channel": "chat",
"public": True,
"time": "2023-11-03T16:38:53.508Z",
"ticket_id": "427406478143",
"id": "16906fb5ce9d57646fa38362_427406478143_W7OU22JH4Q"
},
{
"ticket_id": "513309837",
"channel": "email",
"time": "2024-11-03T16:38:53.508Z",
"body": "I have questions that need answering",
"role": "customer",
"author_id": "customer_abcdef",
"public": true,
"id": "16fb5ce9d57646fa38362_513309837_W7lk22JH4Q"
}
]
}


Create an Attachment

Create an attachment for a specific ticket. This enables attaching photos, audio, files, and video to tickets, complementing the existing ticket and comment creation APIs.

There are two attachment flows available:

  1. Using a presigned URL: Request a presigned URL to securely upload your files directly. Attachments uploaded this way appear in MaestroQA almost immediately.

    • Request: Obtain a presigned URL from the "create attachment" response

    • Upload: Use the presigned URL to upload your file with the specified content_type via a PUT request. Ensure to set the Content-Type and x-amz-server-side-encryption headers (see code examples below)
      Note: presigned URLs are valid for 10 minutes

  2. Using a URL accessible to MaestroQA: Provide a URL where your file is publicly accessible. MaestroQA will asynchronously download and attach the file to your ticket. This process may take several hours, and visibility of the attachment within the application is not immediate.

    • Note: Ensure the URL is accessible to MaestroQA's system. MaestroQA uses static IPS (available upon request) to enable IP whitelisting

Definition

POST https://app.maestroqa.com/api/v1/attachments

Body Parameters

Name

Type

Required

Description

url

string

No

Direct URL of the file to attach (see "Using a URL accessible to MaestroQA" above)

If not specified, this indicates Presigned URL flow and you will receive a presigned_url in the response

ticket_id

string

Yes

The unique identifier of the ticket to which the comment is being added

content_type

string

Yes

The mime type of the file being sent - ex. audio/mp3

id

string

No

Unique id of the attachment - helpful for identifying the attachment, for reference, or potentially stitching. If none is provided, a random ID will be generated and returned in the response.

author_id

string

No

ID of the author (to associate the attachment with a specific agent or customer)

public

boolean

No

If this attachment should create a public or private attachment comment, defaults to true.

timestamp

date string (see formats)

No

The timestamp the attachment's comment should show.

Helpful to ensure comments and attachments show in the proper chronological order.

Defaults to the current time.

Response

The comment that was created

Name

Type

Description

id

string

The unique identifier for the attachment

presigned_url

string

If using Presigned URL flow, the presigned_url to upload your attachment

Example Request for Presigned URL Flow (Python)

import requests

# Create an attachment shell and get a presigned URL from MaestroQA:
url = 'https://app.maestroqa.com/api/v1/attachments'
payload = {
'ticket_id': 'your_ticket_id',
'timestamp': '2022-12-13T05:00:00Z',
'content_type': 'audio/mp3',
}
headers = {'apitoken': 'your_api_token'}

response = requests.post(url, json=payload, headers=headers)
presigned_url = response.json().get('presigned_url')

# Use the presigned URL to upload your file:
with open('path_to_your_file.mp3', 'rb') as file:
upload_headers = {
'Content-Type': 'audio/mp3',
'x-amz-server-side-encryption': 'AES256'
}
upload_response = requests.put(presigned_url, data=file, headers=upload_headers)

Example Request for Accessible URL Flow (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/attachments'
payload = {
'ticket_id': 'your_ticket_id',
'content_type': 'image/png',
'url': 'https://example.com/your_file.png',
}
headers = {'apitoken': 'your_api_token'}

response = requests.post(url, json=payload, headers=headers)


Create an Agent

Definition

POST https://app.maestroqa.com/api/v1/agents

Body Parameters

Name

Type

Required

Description

name

string

Yes

The full name of the agent

available

boolean

Yes

Agent's availability status

email

string

Yes

The email address of the agent

*must be unique (see error responses)

agentGroupId

string

No

The identifier for the agent group the agent should be added to

agentId

string

No

A unique alphanumeric identifier for the agent. If not provided, a random id is generated

*must be unique if provided (see error responses)

Success Response

The agent that was created

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/agents'

payload = {
'name': 'Allison Agent',
'available': True,
'email': 'brand_new_agent@maestroqa.com',
'agentId': 'allisonagent',
'agentGroupId': 'ZBceBjFgQjNY2qLof'
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.post(url, json=payload, headers=headers)

Example Response

{
"_id": "js6LYgg4Ey3EqYhfi",
"name": "Allison Agent",
"agentId": "allisonagent",
"available": true,
"email": "brand_new_agent@maestroqa.com",
"agentGroupId": "ZBceBjFgQjNY2qLof"
}


Update an Agent (add agent id to agent)

Definition

POST https://app.maestroqa.com/api/v1/agents/add-id-to-agent

Body Parameters

Name

Type

Required

Description

email

string

Yes

The email address of the agent

*must be unique (see error responses)

agentId

string

Yes

A unique alphanumeric identifier for the agent.

*must be unique if provided (see error responses)

Success Response

The agent that was updated

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/agents/add-id-to-agent'

payload = {
'email': 'brand_new_agent@maestroqa.com',
'agentId': 'allisonagent'
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.post(url, json=payload, headers=headers)

Update an Agent (update agent availability)

Definition

POST https://app.maestroqa.com/api/v1/update-agent-availability

Body Parameters

Name

Type

Required

Description

email

string

Yes

The email address of the agent

*must be unique (see error responses)

available

boolean

Yes

The value to update agent availability to

Success Response

The agent that was updated

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/update-agent-availability'

payload = {
'email': 'brand_new_agent@maestroqa.com',
'available': True
}

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.post(url, json=payload, headers=headers)


Retrieve a Single To-do

Fetch a single todo item by ID

Definition

GET https://app.maestroqa.com/api/v1/todos/:id

Path Parameters

Name

Type

Description

id

string

The unique identifier of the todo to retrieve

Response

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/todos/CGsTFnNi5P8riTHmC'

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.get(url, headers=headers)

Example Response

{
"id": "CGsTFnNi5P8riTHmC",
"title": "A Todo",
"createdAt": "2023-06-28T16:03:21.089Z",
"updatedAt": "2023-06-28T16:03:30.804Z",
"agentId": "72999",
"creatorId": "HkeYnymy3fhgf3j5F",
"status": "incomplete",
"type": "general",
"coachingSessionIds": [],
"description": "This todo's description text"
}


Retrieve Many To-dos

Fetch multiple todos based on filter criteria.

Definition

GET https://app.maestroqa.com/api/v1/todos

Query Parameters

Name

Type

Description

agentId

string

Filter to only todos for the provided agent ID

creatorId

string

Filter to only todos created by the provided user ID

startDate

date string (see formats)

Filter to only todos created after the provided date

endDate

date string (see formats)

Filter to only todos created before the provided date

count

integer

The number of results to return

startIndex

integer

Offset to start pagination search results

Response

Name

Type

Description

startIndex

integer

Offset of paginated search results

totalResults

integer

Total number of todos that match the provided query filters

itemsPerPage

integer

The number of results per page

Resources

array[todos]

List of todos matching the filter criteria

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/todos'
params = {
'count': 1,
'startIndex': 50,
'startDate': '2023-06-01T15:08:45.781Z',
'endDate': '2023-08-01T15:08:45.781Z',
}
headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.get(url, params=params, headers=headers)

Example Response

{
"startIndex": 50,
"totalResults": 254,
"itemsPerPage": 1,
"Resources": [
{
"id": "P9MTc9MogtHZpDKqm",
"title": "2. My First App",
"createdAt": "2023-06-26T21:01:32.469Z",
"updatedAt": "2023-06-26T21:01:32.469Z",
"agentId": "5595649818",
"creatorId": "zme7PkariKd5Hb4fT",
"status": "incomplete",
"type": "guru",
"answerId": "16906fb5ce9d57646fa38362_5311138_QqJEN5t8LXZRQZd4a_5595649818_GRADER_grading",
"description": ""
}
]
}


Retrieve a Single Coaching Point

Fetch a single coaching point by ID

Definition

GET https://app.maestroqa.com/api/v1/coaching-points/:id

Path Parameters

Name

Type

Description

id

string

The unique identifier of the coaching point to retrieve

Response

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/coaching-points/HHk4xnKwwpYsJHTnq'

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.get(url, headers=headers)

Example Response

{
"id": "6Lt3yHNcBBEyMSK8n",
"createdAt": "2023-06-21T17:52:36.687Z",
"updatedAt": "2023-06-24T05:42:18.599Z",
"agentId": "72999",
"creatorId": "zme7PkariKd5Hb4fT",
"criteriaId": null,
"rubricId": "AatxWWtXWKcfiN34E",
"answerId": "16906fb5ce9d57646fa38362_5310985_AatxWWtXWKcfiN34E_542897_GRADER_grading",
"type": "opportunities",
"classification": "qa",
"coachNotes": "Let's talk about greeting ",
"coachingSessionIds": [],
"textContent": ""
}


Retrieve Many Coaching Points

Fetch multiple coaching points based on filter criteria.

Definition

GET https://app.maestroqa.com/api/v1/coaching-points

Query Parameters

Name

Type

Description

agentId

string

Filter to only coaching points for the provided agent ID

creatorId

string

Filter to only coaching points created by the provided user ID

startDate

date string (see formats)

Filter to only coaching points created after the provided date

endDate

date string (see formats)

Filter to only coaching points created before the provided date

count

integer

The number of results to return

startIndex

integer

Offset to start pagination search results

Response

Name

Type

Description

startIndex

integer

Offset of paginated search results

totalResults

integer

Total number of coaching points that match the provided query filters

itemsPerPage

integer

The number of results per page

Resources

List of coaching points matching the filter criteria

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/coaching-points'
params = {
'count': 3,
'agentId': '72999',
'startDate': '2023-06-01T15:08:45.781Z',
'endDate': '2023-08-01T15:08:45.781Z',
}
headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.get(url, params=params, headers=headers)

Example Response

{
"startIndex": 0,
"totalResults": 16,
"itemsPerPage": 3,
"Resources": [
{
"id": "6Lt3yHNcBBEyMSK8n",
"createdAt": "2023-06-21T17:52:36.687Z",
"updatedAt": "2023-06-24T05:42:18.599Z",
"agentId": "72999",
"creatorId": "zme7PkariKd5Hb4fT",
"criteriaId": null,
"rubricId": "AatxWWtXWKcfiN34E",
"answerId": "16906fb5ce9d57646fa38362_5310985_AatxWWtXWKcfiN34E_542897_GRADER_grading",
"type": "opportunities",
"classification": "qa",
"coachNotes": "Let's talk about greeting",
"coachingSessionIds": [],
"textContent": ""
},
{
"id": "Ai37xkEiq2HPy8zXs",
"createdAt": "2023-07-10T18:10:09.340Z",
"updatedAt": "2023-07-10T18:10:09.340Z",
"agentId": "72999",
"creatorId": "zme7PkariKd5Hb4fT",
"type": "strengths",
"classification": "general",
"coachNotes": "Good job asking probing questions ",
"coachingSessionIds": [
"2TGWZ8YdWnK9HyPgm"
],
"textContent": ""
},
{
"id": "B8wj8BptAFzgjWdti",
"createdAt": "2023-06-23T19:00:00.861Z",
"updatedAt": "2023-06-24T05:42:18.599Z",
"agentId": "72999",
"creatorId": "nQHdkaE76F7upgJwr",
"type": "n/a",
"classification": "general",
"coachNotes": null,
"coachingSessionIds": [],
"textContent": ""
}
]
}


Retrieve a Single Coaching Session

Fetch a single coaching session by ID

Definition

GET https://app.maestroqa.com/api/v1/coaching-sessions/:id

Path Parameters

Name

Type

Description

id

string

The unique identifier of the coaching session to retrieve

Response

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/coaching-sessions/25oWGcmSd34yZRR84'

headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.get(url, headers=headers)

Example Response

{
"id": "25oWGcmSd34yZRR84",
"name": "Sample Coaching Session",
"createdAt": "2023-07-13T16:02:42.255Z",
"updatedAt": "2023-07-13T16:02:53.622Z",
"agentId": "72999",
"agentName": "Harrison Charles",
"coachId": "zme7PkariKd5Hb4fT",
"coachName": "Charlie Smith",
"creatorId": "zme7PkariKd5Hb4fT",
"agentNotes": "Agent's notes",
"coachNotes": "Coach's notes",
"coachPrivateNotes": "Private (not shared with agent) notes",
"sessionContents": "Contents of the sessions's 'Overview' tab",
"coachingTemplateId": "16906fb5ce9d57646fa38362",
"meetingFormat": "inPerson",
"agentConfirmed": false,
"coachConfirmed": false
}


Retrieve Many Coaching Sessions

Fetch multiple coaching sessions based on filter criteria.

Definition

GET https://app.maestroqa.com/api/v1/coaching-sessions

Query Parameters

Name

Type

Description

agentId

string

Filter to only coaching sessions for the provided agent ID

creatorId

string

Filter to only coaching sessions created by the provided user ID

coachId

string

Filter to only coaching sessions where the coach matches the provided user ID

startDate

date string (see formats)

Filter to only coaching sessions created after the provided date

endDate

date string (see formats)

Filter to only coaching sessions created before the provided date

count

integer

The number of results to return

startIndex

integer

Offset to start pagination search results

Response

Name

Type

Description

startIndex

integer

Offset of paginated search results

totalResults

integer

Total number of coaching points that match the provided query filters

itemsPerPage

integer

The number of results per page

Resources

List of coaching sessions matching the filter criteria

Example Request (Python)

import requests

url = 'https://app.maestroqa.com/api/v1/coaching-sessions'
params = {
'count': 3,
'coachId': 'zme7PkariKd5Hb4fT',
'startDate': '2023-06-01T15:08:45.781Z',
'endDate': '2023-08-01T15:08:45.781Z',
}
headers = { 'apitoken': 'YOUR_API_TOKEN' }

response = requests.get(url, params=params, headers=headers)

Example Response

{
"startIndex": 0,
"totalResults": 253,
"itemsPerPage": 3,
"Resources": [
{
"id": "25oWGcmSd34yZRR84",
"name": "Sample Coaching Session",
"createdAt": "2023-07-13T16:02:42.255Z",
"updatedAt": "2023-07-13T16:02:53.622Z",
"agentId": "72999",
"agentName": "Harrison Charles",
"coachId": "zme7PkariKd5Hb4fT",
"coachName": "Charlie Smith",
"creatorId": "zme7PkariKd5Hb4fT",
"agentNotes": "Agent's notes",
"coachNotes": "Coach's notes",
"coachPrivateNotes": "Private (not shared with agent) notes",
"sessionContents": "Contents of the sessions's 'Overview' tab",
"coachingTemplateId": "16906fb5ce9d57646fa38362",
"meetingFormat": "inPerson",
"agentConfirmed": false,
"coachConfirmed": false
},
{
"id": "2BNoiJDcthvabPyxC",
"name": "Created by Matthew",
"createdAt": "2023-06-22T21:09:25.511Z",
"updatedAt": "2023-07-26T21:05:24.878Z",
"agentId": "0055e000000ZIqdAAG",
"agentName": "Automated Process",
"coachId": "zme7PkariKd5Hb4fT",
"coachName": "Matthew Chuck",
"creatorId": "zme7PkariKd5Hb4fT",
"agentNotes": "",
"coachNotes": "",
"coachPrivateNotes": "",
"sessionContents": "Performance\nAgent perspective on their performance since last review\nHow do you feel about your recent performance?\nHave you been experiencing any blockers in your workflow? Is there any additional support you need?\n\nGrowth\nDiscuss areas that the Agent has grown or excelled in. How has this contributed to their overall performance and their team’s?\n \n \n\nDevelopment Goals\nWhat career goals do you want to achieve in the coming quarter or year? What skills or competencies do you want to hone in on?\n\nThis Coming Quarter\n \n \n\nThis Coming Year\n \n \n\n",
"coachingTemplateId": "16906fb5ce9d57646fa38362_3",
"meetingFormat": "inPerson",
"agentConfirmed": false,
"coachConfirmed": false
},
{
"id": "2BendGuN7JqrKfRGn",
"name": "test coaching session",
"createdAt": "2023-06-03T04:02:13.764Z",
"updatedAt": "2023-06-03T04:02:30.120Z",
"agentId": "72999",
"agentName": "Harrison Hunter Rill",
"coachId": "zme7PkariKd5Hb4fT",
"coachName": "Harrison Hunter2",
"creatorId": "zme7PkariKd5Hb4fT",
"agentNotes": "",
"coachNotes": "",
"coachPrivateNotes": "",
"sessionContents": "",
"coachingTemplateId": "16906fb5ce9d57646fa38362_2",
"meetingFormat": "inPerson",
"agentConfirmed": false,
"coachConfirmed": true
}
]
}


Create a Metric

Create a metric and associate to a specific ticket and agent. Note a metric is defined by combination of the metric id, ticket id, source id and agent id. Meaning every metric is specific to an agent and a ticket. To create a ticket attribute that is not agent specific, you can use the normal Tickets API MaestroQA API.

Definition

POST => https://app.maestroqa.com/api/v1/ticket-metrics

Body Parameters

Name

Type

Required

Description

ticket_id

string

Yes

Ticket ID of the ticket the metric is attached to

source_id

string

Yes

The identifier of the source of the ticket. Important when there are multiple help desks or ticket source systems to ensure proper ticket identification especially if there can be overlapping ids. Ex. salesforce

agent_id

string

Yes

The agent ID or email of the ticket the metric is attached to. Note this agent_id must be associated with an agent in MaestroQA. See the SCIM API SCIM | Maestro QA Help Center if you need to dynamically fetch agent ids or emails.

metric_id

string

Yes

The metric ID of the metric you are passing. Ex. response_time

metric_value

number

Yes

The value for the metric you are passing. Ex. 17

timestamp

string

Yes

The timestamp the metric comment should count for - ie when this metric “occurred”. Often this is something like the time the update or comment that generated the metric occurred or the ticket creation time.

Expects ISO Format date string of this format: 2017-12-13T05:00:00Z

ticket_event_id

string

No

Identifier for sub event w/i a case - for example get survey id for CSAT/CES metrics, can be null for metrics that do not have a sub event

metric_deleted

boolean

No

Use this to remove a metric from a ticket. For example, you could post a metric for a ticket. Then later, if that metric is no longer relevant, rather than setting it to zero, post metric_deleted as true and the metric will be disassociated from the ticket.

Response

The metric that was created

Name

Type

Description

ticket_id

string

Ticket ID of the ticket the metric is attached to

metric_id

string

The metric ID of the metric you are passing. Ex. response_time

Example Request (Python)

import requests

individual_endpoint = 'https://app.maestroqa.com/api/v1/ticket-metrics'

headers = {
'Content-Type': 'application/json',
'apitoken': 'YOUR_API_TOKEN'
}

# individual
individual_data = {
'ticket_id': '1234',
'source_id': 'internal_crm',
'agent_id': '456',
'metric_id': 'response_time',
'metric_value': 32,
'timestamp': '2017-12-13T05:00:00Z'
'metric_deleted': False,
}
res1 = requests.post(individual_endpoint, json=individual_data, headers=headers)
res1.status_code
# => 201

# bulk
bulk_data = {
batch: [individual_data, …] # many instances of individual data
}
res2 = requests.post(bulk_endpoint, json=bulk_data, headers=headers)
res2.status_code
# => 201

Example Response

{
"ticket_id": "1234",
"metric_id": "response_time"
}

Create Many Metrics

Create a batch of metrics for one or more tickets.

Definition

https://app.maestroqa.com/api/v1/ticket-metrics-batch

Body Parameters

Name

Type

Required

Description

batch

array

Yes

Array of metric objects (see structure of a "metric" object from Create a Metric request arguments)

*Note: there is a maximum of 500 comments per batch

Response

The metrics that were created

Name

Type

Description

results

array

Array of created metric objects (see structure of a "metric" response from Create a Metric response documentation)

Example Request (Python)

import requests

bulk_endpoint = 'https://app.maestroqa.com/api/v1/ticket-metrics-batch'

headers = {
'Content-Type': 'application/json',
'apitoken': 'YOUR_API_TOKEN'
}

# individual
individual_data = {
'ticket_id': '1234',
'source_id': 'internal_crm',
'agent_id': '456',
'metric_id': 'response_time',
'metric_value': 32,
'timestamp': '2017-12-13T05:00:00Z'
'metric_deleted': False,
}
res1 = requests.post(individual_endpoint, json=individual_data, headers=headers)
res1.status_code
# => 201

# bulk
bulk_data = {
batch: [individual_data, …] # many instances of individual data
}
res2 = requests.post(bulk_endpoint, json=bulk_data, headers=headers)
res2.status_code
# => 201

Example Response

{
"results": [
{
"ticket_id": "1234",
"metric_id": "response_time"
},
{
"ticket_id": "12345",
"metric_id": "response_time"
}
]
}


Rate Limits

A given token has limits on how many times it can be used to make a request. The general guidelines to refer to are:

  • 10 requests per second

  • 100 requests per minute

You can expect to export 10,000 to 50,000 scores at time. The exact number is variable based on the size of your scorecard, number of comments per scorecard, and other factors.

Error Responses

Common error response scenarios:

    • cause: invalid API token

    • likely cause: request made for non-existent content (for example, making a "Get User" request for a user that has been deleted)

    • likely cause: a non-unique value was provided for a parameter that must be unique (for example, making "Create Agent" request with an email that is already in use by an existing agent)

      • the error response message will indicate which values were in conflict

    • likely cause: invalid values provided for one or more request parameters

      • the error response message will indicate which parameters were invalid

    • cause: exceeded rate limit

Troubleshooting

  • "Body Parameters" is not be confused with "Query Parameters". For example when using Postman, see the below screenshots clarifying the difference,

Query Parameters:

Body Parameters:

Did this answer your question?