Conversations API
A conversation is one interview between the AI and one respondent. The API returns who the respondent is, the AI summary with one answer per question, and the full transcript. For authentication, pagination and errors, see the API overview.
List conversations#
HTTP
GET /api/v1/projects/{project_id}/conversationsReturns a project's conversations, newest first, each with its AI summary. Transcripts are left out of the list. Fetch them with Get a conversation.
Query parameters#
| Parameter | Description |
|---|---|
status | One or more of invited, opened, started, completed, cancelled, separated by commas. Without it, every status except invited is returned. |
sentiment | One or more of positive, negative, neutral, mixed, separated by commas |
created_after | Only conversations created at or after this ISO 8601 time, such as 2026-05-01T00:00:00Z |
created_before | Only conversations created at or before this time |
search | Text to look for in summaries, quotes and respondent details. Up to 200 characters. |
limit | 1 to 100. Default 25. |
cursor | The next_cursor of the previous page |
Only completed conversations have a full summary, so most integrations send status=completed.
Example#
curl -G "https://diaform.io/api/v1/projects/b8acb3ab-1f3d-4a7e-a846-b7f493f86b6d/conversations" \
-H "Authorization: Bearer $DIAFORM_API_KEY" \
--data-urlencode "status=completed" \
--data-urlencode "sentiment=negative,mixed" \
--data-urlencode "created_after=2026-05-01T00:00:00Z" \
--data-urlencode "limit=50"Response#
JSON
{
"data": [
{
"id": "0f8d43a2-6df9-49c8-bf5d-fd2b6ec2d9ee",
"project_id": "b8acb3ab-1f3d-4a7e-a846-b7f493f86b6d",
"status": "completed",
"created_at": "2026-05-07T12:00:00.123456+00:00",
"started_at": "2026-05-07T12:01:11.482913+00:00",
"ended_at": "2026-05-07T12:15:41.204+00:00",
"duration_seconds": 870,
"country": "DE",
"overall_sentiment": "mixed",
"respondent": {
"label": "alex@acme.com",
"email": null,
"identities": [
{ "type": "email", "value": "alex@acme.com", "source": "owner" },
{ "type": "name", "value": "Alex", "source": "ai" }
]
},
"metadata": {},
"invite": {
"id": "3a4f49c7-b8f4-4c44-8f74-fd8e4277c3e4",
"status": "completed",
"created_at": "2026-05-07T12:00:00.123456+00:00",
"opened_at": "2026-05-07T12:01:11.482913+00:00",
"completed_at": "2026-05-07T12:15:41.204+00:00"
},
"summary": {
"overall_sentiment": "mixed",
"answers": [
{
"question_id": "V1StGXR8_Z5jdHi6B-myT",
"question": "How did your first week with the product go?",
"summary": "Setup was quick, but inviting teammates was confusing.",
"sentiment": "mixed",
"confidence": "high",
"quotes": ["I had no idea where the invite button was"]
}
],
"urgent_issues": [],
"additional_insights": "Would pay more for a Slack integration."
}
}
],
"has_more": true,
"next_cursor": "WyIyMDI2LTA1LTA3VDEyOjAwOjAwLjEyMzQ1NiswMDowMCIsIjBmOGQ0M2EyIl0"
}Conversation fields#
| Field | Type | Description |
|---|---|---|
id | string | Conversation ID, the same one webhooks send as conversation_id |
project_id | string | The project it belongs to |
status | string | invited, opened, started, completed or cancelled. The dashboard shows started as In progress. |
created_at | string | When the conversation was created. For invites, that's when the invite was created. |
started_at | string or null | When the interview started |
ended_at | string or null | When the conversation was completed or cancelled |
duration_seconds | number or null | Time from start to end |
country | string or null | The respondent's country code, when known |
overall_sentiment | string or null | positive, negative, neutral or mixed. Same as summary.overall_sentiment. |
respondent.label | string or null | The best name for the respondent: their email, then their name, then another identity |
respondent.email | string or null | Legacy field, null for new conversations. Read emails from respondent.identities. |
respondent.identities | array | Everything known about the respondent. source is owner (you supplied it), ai (extracted from their messages) or system (added by Diaform). |
metadata | object | Empty for invites and direct links. For embedded conversations it holds embed details such as "embed": true and embed_parent_origin. |
invite | object or null | Invite details when the conversation came from a respondent invite, otherwise null |
summary | object or null | The AI summary. null until the conversation ends and the summary is ready. |
Summary fields#
| Field | Type | Description |
|---|---|---|
overall_sentiment | string | positive, negative, neutral or mixed |
answers | array | One entry per question the respondent was asked |
answers[].question_id | string | The question's ID in the project |
answers[].question | string | The question as it was asked |
answers[].summary | string | A short summary of the answer |
answers[].sentiment | string | positive, negative, neutral or mixed |
answers[].confidence | string | high, medium or low: how fully the question was answered |
answers[].quotes | array | Notable quotes in the respondent's own words. Often empty. |
urgent_issues | array | Critical problems the respondent raised, as short strings |
additional_insights | string or null | Useful feedback that didn't belong to any question |
Get a conversation#
HTTP
GET /api/v1/conversations/{conversation_id}Returns one conversation with every field of the list, plus the transcript in messages.
Example#
curl "https://diaform.io/api/v1/conversations/0f8d43a2-6df9-49c8-bf5d-fd2b6ec2d9ee" \
-H "Authorization: Bearer $DIAFORM_API_KEY"Response#
The fields shared with the list are shortened here.
JSON
{
"id": "0f8d43a2-6df9-49c8-bf5d-fd2b6ec2d9ee",
"project_id": "b8acb3ab-1f3d-4a7e-a846-b7f493f86b6d",
"status": "completed",
"overall_sentiment": "mixed",
"summary": {},
"messages": [
{
"role": "interviewer",
"text": "Hi! Thanks for taking the time. How did your first week with the product go?"
},
{
"role": "respondent",
"text": "Setup was fast. But I had no idea where the invite button was."
},
{
"role": "interviewer",
"text": "Where did you expect to find it?"
}
]
}| Field | Type | Description |
|---|---|---|
messages | array | The transcript in order. Empty when the respondent never replied. |
messages[].role | string | interviewer (the AI) or respondent |
messages[].text | string | What was said. Spoken answers appear as their transcription, and a choice or rating as text such as Selected answers: Pro. |