Export Agent Conversations
curl --request GET \
--url https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export \
--header 'Authorization: Bearer <token>'import requests
url = "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export"
headers = {"Authorization": "Bearer <token>"}
response = requests.get(url, headers=headers)
print(response.text)const options = {method: 'GET', headers: {Authorization: 'Bearer <token>'}};
fetch('https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "GET",
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"net/http"
"io"
)
func main() {
url := "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export"
req, _ := http.NewRequest("GET", url, nil)
req.Header.Add("Authorization", "Bearer <token>")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.get("https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export")
.header("Authorization", "Bearer <token>")
.asString();require 'uri'
require 'net/http'
url = URI("https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Get.new(url)
request["Authorization"] = 'Bearer <token>'
response = http.request(request)
puts response.read_body{
"success": true,
"message": "<string>",
"data": [
{
"userEmail": "<string>",
"userName": "<string>",
"userPhone": "<string>",
"userAddress": "<string>",
"userCompany": "<string>",
"userWebsite": "<string>",
"notes": "<string>",
"userProfilePic": "<string>",
"stage": "new",
"value": 123,
"currency": "<string>",
"expectedCloseDate": "<string>",
"subIndustry": "<string>",
"source": "<string>",
"language": "<string>",
"linkedIn": "<string>",
"facebook": "<string>",
"instagram": "<string>",
"demoDate": "<string>",
"demoTime": "<string>",
"demoLink": "<string>",
"lostReason": "<string>",
"lastActivityDate": "<string>",
"ID": "<string>",
"userID": "<string>",
"campaignId": "<string>",
"userImage": "<string>",
"socialHandle": "<string>",
"isFollowingBusiness": true,
"socialVerified": true,
"userOs": "<string>",
"userBrowser": "<string>",
"ipAddress": "<string>",
"browserTimezone": "<string>",
"countryCode": "<string>",
"origin": "<unknown>",
"whatsappPhoneNumberId": "<string>",
"whatsappBusinessNumber": "<string>",
"whatsappDisplayPhoneNumber": "<string>",
"whatsappBusinessAccountId": "<string>",
"voiceflowV4Session": {
"sessionKey": "<string>",
"projectId": "<string>",
"environmentAlias": "<string>",
"updatedAt": 123,
"resolvedRuntime": "legacy"
},
"messagesNum": 123,
"interactionsNum": 123,
"ts": 123,
"tags": [
"<string>"
],
"convoTimeSeconds": 123,
"firstMessageTS": 123,
"lastMessageTS": 123,
"userPlatform": "<string>",
"state": "requested_chat",
"smbContact": true,
"smbContactName": "<string>",
"smbContactRemovedAt": 123,
"smbLastSeenAt": 123,
"humanClaimedAt": 123,
"humanLastRepliedAt": 123,
"pendingAiReplyAt": 123,
"chatAssignedTo": "<string>",
"chatAssignedToIds": [
"<string>"
],
"assignedToUsers": [
{
"userId": "<string>",
"name": "<string>",
"email": "<string>",
"photoUrl": "<string>",
"note": "<string>",
"assignedAt": "<string>",
"status": "pending"
}
],
"handoffHistory": [
{
"requestedAt": 123,
"acceptedAt": 123,
"completedAt": 123,
"acceptedBy": "<string>",
"organizationId": "<string>",
"requestedTeamKey": "<string>",
"teamIds": [
"<string>"
],
"teamKeys": [
"<string>"
]
}
],
"isTyping": true,
"lastModified": 123,
"sessionsNum": 123,
"lang": "<string>",
"vapi": {
"cost": 123,
"callDuration": 123,
"recordingUrl": "<string>",
"syncRecordingUrl": "<string>",
"callerPhoneNumber": "<string>",
"calleePhoneNumber": "<string>",
"callStatus": "<string>",
"callError": "<string>"
},
"ratingFrom5": 123,
"totalUserInteractions": 123,
"isBlocked": true,
"nodesInfo": {
"currentNode": "<string>"
},
"capturedVariables": "<unknown>",
"campaignCalls": [
"<unknown>"
],
"sessions": [
"<unknown>"
],
"endReason": "<string>",
"isTest": true,
"metrics": [
"<unknown>"
],
"notifyToUserId": "<string>",
"averageLatency": 123,
"voice": {
"latestSessionId": "<string>",
"listenUrl": "<string>",
"listenUrlUNIX": 123
},
"detailedCost": {
"totalCreditsConsumed": 123,
"speechGenCost": 123,
"transcriberCost": 123,
"twilioCost": 123,
"llmCost": 123
},
"summary": "<string>",
"shortSummary": "<string>",
"requestedTeamKey": "<string>",
"delegatedBy": "<string>",
"delegatedAt": 123,
"lastViewed": 123,
"isArchived": true,
"archivedAt": 123,
"archivedBy": "<string>",
"isResolved": true,
"resolvedAt": 123,
"resolvedBy": "<string>",
"resolvedByEmail": "<string>",
"lastResolvedAssigneeId": "<string>",
"reopenedAt": 123,
"reopenReason": "<string>",
"csat": {
"satisfaction10": 5.5,
"ease10": 5.5,
"comment": "<string>",
"submittedAt": 123,
"channel": "<string>",
"surveyVersion": 123
},
"note": "<string>",
"assignedTo": {
"userId": "<string>",
"name": "<string>",
"email": "<string>",
"photoUrl": "<string>",
"note": "<string>",
"assignedAt": "<string>",
"status": "pending"
},
"hotScore": 123,
"hotLabel": "hot",
"crmActivities": [
{
"type": "Message",
"id": "<string>",
"title": "<string>",
"date": "<string>",
"dueDate": "<string>",
"completed": true,
"responded": true,
"firstChannel": "LinkedIn",
"firstEngaged": true,
"secondChannel": "LinkedIn",
"secondEngaged": true,
"note": "<string>",
"notesHistory": [
{
"text": "<string>",
"agentId": "<string>",
"agentName": "<string>",
"timestamp": "<string>"
}
],
"metadata": {}
}
],
"crmAlerts": {
"overdueECD": true,
"overdueActivity": true,
"staleLead": true,
"responded": true,
"newHandoffAssigned": true
},
"contactIdentityId": "<string>",
"linkedChannels": [
"<string>"
],
"crossChannelContext": "<string>",
"leadScore": 0,
"funnelStepsMatched": [],
"funnelScoreHistory": [],
"funnelNotificationSent": false,
"funnelLastEvaluated": 123,
"funnelExtractedData": {},
"funnelSummary": "<string>",
"tokenUsage": {
"cumulativeInputTokens": 123,
"cumulativeOutputTokens": 123,
"cumulativeTotalTokens": 123,
"cumulativeUsd": 123,
"lastTurnInputTokens": 123,
"lastTurnOutputTokens": 123,
"lastTurnTotalTokens": 123,
"lastTurnUsd": 123,
"lastTurnModelId": "<string>",
"lastTurnContextWindow": 123,
"lastTurnInputUsdPer1k": 123,
"lastTurnOutputUsdPer1k": 123,
"lastTurnTs": 123,
"usagePerModel": {}
},
"inboundEngagementState": {
"firstDecisionAt": 123,
"firstDecisionShouldReply": true,
"lastDecisionAt": 123,
"lastDecisionShouldReply": true,
"lastDecisionReason": "<string>",
"aiOwnedThread": true,
"ignoreThread": true,
"lastTriggeredBy": "phrase"
}
}
],
"usage": {
"periodKey": "<string>",
"billableUsedThisRequest": 123,
"billableUsedThisPeriod": 123,
"includedQuota": 123,
"billableRemainingThisPeriod": 123,
"overageUsedThisPeriod": 123,
"overagePacksCharged": 123,
"exportRequestCount": 123,
"summary": "<string>",
"logId": "<string>"
},
"rateLimit": {
"requestsPerHour": 123,
"remainingHour": 123
},
"hasMore": true,
"nextCursor": "<string>",
"limit": 123,
"mode": "paginated",
"scannedConvoCount": 123,
"source": "supabase",
"query": {
"sort": "desc",
"fromTs": 123,
"toTs": 123
}
}{
"message": "<string>",
"code": "<string>",
"issues": [
{
"message": "<string>"
}
]
}Conversations
Export Agent Conversations
Export chat sessions via the V3 Chat Export API — paginated by default (newest first), with sort and date-range filters. Reads from the PG mirror. Requires a paid workspace (hasEverPaid).
GET
/
agents
/
{agentId}
/
convos
/
export
Export Agent Conversations
curl --request GET \
--url https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export \
--header 'Authorization: Bearer <token>'import requests
url = "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export"
headers = {"Authorization": "Bearer <token>"}
response = requests.get(url, headers=headers)
print(response.text)const options = {method: 'GET', headers: {Authorization: 'Bearer <token>'}};
fetch('https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "GET",
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"net/http"
"io"
)
func main() {
url := "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export"
req, _ := http.NewRequest("GET", url, nil)
req.Header.Add("Authorization", "Bearer <token>")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.get("https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export")
.header("Authorization", "Bearer <token>")
.asString();require 'uri'
require 'net/http'
url = URI("https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Get.new(url)
request["Authorization"] = 'Bearer <token>'
response = http.request(request)
puts response.read_body{
"success": true,
"message": "<string>",
"data": [
{
"userEmail": "<string>",
"userName": "<string>",
"userPhone": "<string>",
"userAddress": "<string>",
"userCompany": "<string>",
"userWebsite": "<string>",
"notes": "<string>",
"userProfilePic": "<string>",
"stage": "new",
"value": 123,
"currency": "<string>",
"expectedCloseDate": "<string>",
"subIndustry": "<string>",
"source": "<string>",
"language": "<string>",
"linkedIn": "<string>",
"facebook": "<string>",
"instagram": "<string>",
"demoDate": "<string>",
"demoTime": "<string>",
"demoLink": "<string>",
"lostReason": "<string>",
"lastActivityDate": "<string>",
"ID": "<string>",
"userID": "<string>",
"campaignId": "<string>",
"userImage": "<string>",
"socialHandle": "<string>",
"isFollowingBusiness": true,
"socialVerified": true,
"userOs": "<string>",
"userBrowser": "<string>",
"ipAddress": "<string>",
"browserTimezone": "<string>",
"countryCode": "<string>",
"origin": "<unknown>",
"whatsappPhoneNumberId": "<string>",
"whatsappBusinessNumber": "<string>",
"whatsappDisplayPhoneNumber": "<string>",
"whatsappBusinessAccountId": "<string>",
"voiceflowV4Session": {
"sessionKey": "<string>",
"projectId": "<string>",
"environmentAlias": "<string>",
"updatedAt": 123,
"resolvedRuntime": "legacy"
},
"messagesNum": 123,
"interactionsNum": 123,
"ts": 123,
"tags": [
"<string>"
],
"convoTimeSeconds": 123,
"firstMessageTS": 123,
"lastMessageTS": 123,
"userPlatform": "<string>",
"state": "requested_chat",
"smbContact": true,
"smbContactName": "<string>",
"smbContactRemovedAt": 123,
"smbLastSeenAt": 123,
"humanClaimedAt": 123,
"humanLastRepliedAt": 123,
"pendingAiReplyAt": 123,
"chatAssignedTo": "<string>",
"chatAssignedToIds": [
"<string>"
],
"assignedToUsers": [
{
"userId": "<string>",
"name": "<string>",
"email": "<string>",
"photoUrl": "<string>",
"note": "<string>",
"assignedAt": "<string>",
"status": "pending"
}
],
"handoffHistory": [
{
"requestedAt": 123,
"acceptedAt": 123,
"completedAt": 123,
"acceptedBy": "<string>",
"organizationId": "<string>",
"requestedTeamKey": "<string>",
"teamIds": [
"<string>"
],
"teamKeys": [
"<string>"
]
}
],
"isTyping": true,
"lastModified": 123,
"sessionsNum": 123,
"lang": "<string>",
"vapi": {
"cost": 123,
"callDuration": 123,
"recordingUrl": "<string>",
"syncRecordingUrl": "<string>",
"callerPhoneNumber": "<string>",
"calleePhoneNumber": "<string>",
"callStatus": "<string>",
"callError": "<string>"
},
"ratingFrom5": 123,
"totalUserInteractions": 123,
"isBlocked": true,
"nodesInfo": {
"currentNode": "<string>"
},
"capturedVariables": "<unknown>",
"campaignCalls": [
"<unknown>"
],
"sessions": [
"<unknown>"
],
"endReason": "<string>",
"isTest": true,
"metrics": [
"<unknown>"
],
"notifyToUserId": "<string>",
"averageLatency": 123,
"voice": {
"latestSessionId": "<string>",
"listenUrl": "<string>",
"listenUrlUNIX": 123
},
"detailedCost": {
"totalCreditsConsumed": 123,
"speechGenCost": 123,
"transcriberCost": 123,
"twilioCost": 123,
"llmCost": 123
},
"summary": "<string>",
"shortSummary": "<string>",
"requestedTeamKey": "<string>",
"delegatedBy": "<string>",
"delegatedAt": 123,
"lastViewed": 123,
"isArchived": true,
"archivedAt": 123,
"archivedBy": "<string>",
"isResolved": true,
"resolvedAt": 123,
"resolvedBy": "<string>",
"resolvedByEmail": "<string>",
"lastResolvedAssigneeId": "<string>",
"reopenedAt": 123,
"reopenReason": "<string>",
"csat": {
"satisfaction10": 5.5,
"ease10": 5.5,
"comment": "<string>",
"submittedAt": 123,
"channel": "<string>",
"surveyVersion": 123
},
"note": "<string>",
"assignedTo": {
"userId": "<string>",
"name": "<string>",
"email": "<string>",
"photoUrl": "<string>",
"note": "<string>",
"assignedAt": "<string>",
"status": "pending"
},
"hotScore": 123,
"hotLabel": "hot",
"crmActivities": [
{
"type": "Message",
"id": "<string>",
"title": "<string>",
"date": "<string>",
"dueDate": "<string>",
"completed": true,
"responded": true,
"firstChannel": "LinkedIn",
"firstEngaged": true,
"secondChannel": "LinkedIn",
"secondEngaged": true,
"note": "<string>",
"notesHistory": [
{
"text": "<string>",
"agentId": "<string>",
"agentName": "<string>",
"timestamp": "<string>"
}
],
"metadata": {}
}
],
"crmAlerts": {
"overdueECD": true,
"overdueActivity": true,
"staleLead": true,
"responded": true,
"newHandoffAssigned": true
},
"contactIdentityId": "<string>",
"linkedChannels": [
"<string>"
],
"crossChannelContext": "<string>",
"leadScore": 0,
"funnelStepsMatched": [],
"funnelScoreHistory": [],
"funnelNotificationSent": false,
"funnelLastEvaluated": 123,
"funnelExtractedData": {},
"funnelSummary": "<string>",
"tokenUsage": {
"cumulativeInputTokens": 123,
"cumulativeOutputTokens": 123,
"cumulativeTotalTokens": 123,
"cumulativeUsd": 123,
"lastTurnInputTokens": 123,
"lastTurnOutputTokens": 123,
"lastTurnTotalTokens": 123,
"lastTurnUsd": 123,
"lastTurnModelId": "<string>",
"lastTurnContextWindow": 123,
"lastTurnInputUsdPer1k": 123,
"lastTurnOutputUsdPer1k": 123,
"lastTurnTs": 123,
"usagePerModel": {}
},
"inboundEngagementState": {
"firstDecisionAt": 123,
"firstDecisionShouldReply": true,
"lastDecisionAt": 123,
"lastDecisionShouldReply": true,
"lastDecisionReason": "<string>",
"aiOwnedThread": true,
"ignoreThread": true,
"lastTriggeredBy": "phrase"
}
}
],
"usage": {
"periodKey": "<string>",
"billableUsedThisRequest": 123,
"billableUsedThisPeriod": 123,
"includedQuota": 123,
"billableRemainingThisPeriod": 123,
"overageUsedThisPeriod": 123,
"overagePacksCharged": 123,
"exportRequestCount": 123,
"summary": "<string>",
"logId": "<string>"
},
"rateLimit": {
"requestsPerHour": 123,
"remainingHour": 123
},
"hasMore": true,
"nextCursor": "<string>",
"limit": 123,
"mode": "paginated",
"scannedConvoCount": 123,
"source": "supabase",
"query": {
"sort": "desc",
"fromTs": 123,
"toTs": 123
}
}{
"message": "<string>",
"code": "<string>",
"issues": [
{
"message": "<string>"
}
]
}Requires a paid workspace (
hasEverPaid). Reads conversation content from the Postgres/Supabase mirror only (not Firestore). Each billable human-message session counts toward the monthly quota (50,000 included; overage billed in packs of 1,000).Modes
| Mode | How | Behavior |
|---|---|---|
| Paginated (default) | Omit convoIds | Returns a page of chats from the Postgres mirror. Newest first by default. Use cursor / hasMore to page through. |
| Selected | Pass convoIds=id1,id2,... | Exports only those conversation IDs (max 200 per request). |
Query parameters
| Param | Default | Description |
|---|---|---|
limit | 20 | Page size in paginated mode (max 50). |
sort | desc | desc = most recent chats first; asc = oldest first. |
fromTs | — | Inclusive start of range (unix seconds; ms also accepted). |
toTs | — | Inclusive end of range (unix seconds; ms also accepted). |
cursor | — | Opaque cursor from the previous response’s nextCursor. Keep the same sort / fromTs / toTs when paging. |
convoIds | — | Comma-separated IDs for selected mode (skips pagination). |
format | json | Response format. |
Rate limits
Per workspace (authenticated owner). In-memory counters (single process). Response includesrateLimit.remainingHour so clients can back off before a 429.
| Limit | Unpaid | Paid (hasEverPaid) |
|---|---|---|
| Paginated page size | default 20, max 50 | default 20, max 100 |
Selected convoIds per request | 200 | 500 |
| Export requests per hour | 300 | 1,500 |
hasEverPaid, so live callers use the paid column. 429 when exceeded.
Examples
Newest chats (default)
curl -G "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export" \
-H "Authorization: Bearer {SECRET_API_KEY}" \
--data-urlencode "limit=20"
Oldest first
curl -G "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export" \
-H "Authorization: Bearer {SECRET_API_KEY}" \
--data-urlencode "sort=asc" \
--data-urlencode "limit=20"
Date range (unix seconds)
# e.g. 2026-01-01 .. 2026-01-31 UTC
curl -G "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export" \
-H "Authorization: Bearer {SECRET_API_KEY}" \
--data-urlencode "fromTs=1735689600" \
--data-urlencode "toTs=1738367999" \
--data-urlencode "sort=desc" \
--data-urlencode "limit=50"
Next page
curl -G "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export" \
-H "Authorization: Bearer {SECRET_API_KEY}" \
--data-urlencode "limit=20" \
--data-urlencode "sort=desc" \
--data-urlencode "cursor={nextCursor_from_previous_response}"
Specific conversation IDs
curl -G "https://eu-gcp-api.vg-stuff.com/v3/agents/{agentId}/convos/export" \
-H "Authorization: Bearer {SECRET_API_KEY}" \
--data-urlencode "convoIds=convo_a,convo_b,convo_c"
Example response (paginated)
{
"success": true,
"message": "Exported 12 conversation(s) (15 billable session(s)). Paginated newest-first (supabase). ...",
"mode": "paginated",
"source": "supabase",
"limit": 20,
"hasMore": true,
"nextCursor": "eyJ2IjoxLCJzb3J0IjoiZGVzYyIsInVuaXF1ZUlkIjoiLi4uIn0",
"scannedConvoCount": 20,
"query": {
"sort": "desc",
"fromTs": null,
"toTs": null
},
"usage": {
"periodKey": "billing_...",
"billableUsedThisRequest": 15,
"billableUsedThisPeriod": 120,
"includedQuota": 50000,
"billableRemainingThisPeriod": 49880,
"summary": "Used 120 / 50,000 billable session exports this billing cycle..."
},
"data": []
}
Notes
- Reads from the Supabase
convosmirror (convoTurns+convoSessions), not live Firestore. - Default sort is most recent first (
sort=desc). fromTs/toTsfilter on the conversation’stsfield (inclusive).- When paging, reuse the same
sort,fromTs, andtoTswithcursor. - Conversations with no human messages are skipped (not billable).
- Past sessions under a convo that contain human turns are each billable.
- Response includes
usagefor quota tracking.
Related documentation
Authorizations
Bearer authentication header of the form Bearer <token>, where <token> is your auth token.
Path Parameters
Query Parameters
Available options:
csv, json Required range:
1 <= x <= 100Available options:
desc, asc Response
Successful response
Show child attributes
Show child attributes
Show child attributes
Show child attributes
Show child attributes
Show child attributes
Available options:
paginated, selected Available options:
supabase Show child attributes
Show child attributes
