REST API reference
Endpoints, permissions, fields and responses for TruCom REST API v1.
Base URL and conventions
Base URL: https://trucom.app/api/v1/rest. Authenticate every request with Authorization: Bearer YOUR_API_KEY. Send application/json for writes. Resource IDs are public ULIDs. All endpoints return JSON and Cache-Control: private, no-store.
Each endpoint below names its exact required scope. List responses use data as an array with meta.pagination. Single-resource responses use data as an object with meta. All list endpoints accept per_page (1–100, default 25) and cursor.
GET /me
Return the workspace, widget, granted scopes and key expiry. Any valid API key can call this endpoint.
Permission: any active API key. Success: 200. Response schema: ApiContextResponse.
curl -X GET "https://trucom.app/api/v1/rest/me" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json"{
"data": {
"workspace": {
"id": "01K8V8GHVQ90RYQRJQKEF3Q9A1",
"name": "Your workspace"
},
"widget_id": "01K8V8GHVQ90RYQRJQKEF3Q9A2",
"scopes": [
"customers:read"
],
"expires_at": "2027-01-25T10:00:00+00:00"
},
"meta": []
}GET /customers
Return active customer profiles in creation order. Merged profiles are excluded. List responses omit widget_context.
Permission: customers:read. Success: 200. Response schema: CustomerListResponse.
curl -X GET "https://trucom.app/api/v1/rest/customers?per_page=25" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json"{
"data": [
{
"id": "01K8V8GHVQ90RYQRJQKEF3Q9AZ",
"name": "Alex Morgan",
"email": "[email protected]",
"phone": null,
"company": "Example Co",
"external_id": "account-1042",
"attributes": {
"plan": "Business"
},
"tags": [],
"is_anonymous": false,
"source": "api",
"first_seen_at": "2026-10-27T10:00:00+00:00",
"last_seen_at": "2026-10-27T10:00:00+00:00",
"created_at": "2026-10-27T10:00:00+00:00",
"updated_at": "2026-10-27T10:00:00+00:00"
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. Maximum records per page. |
| query | cursor | string | Optional. Use meta.pagination.next_cursor unchanged. |
GET /customers/lookup
Provide exactly one of email, phone or external_id. Matching uses TruCom identity normalization; it is exact, not fuzzy. External IDs are trimmed, whitespace-normalized and case-insensitive. Phone values remove formatting and preserve international + prefixes.
Permission: customers:read. Success: 200. Response schema: CustomerResponse.
curl -X GET "https://trucom.app/api/v1/rest/customers/lookup?external_id=account-1042" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json"{
"data": {
"id": "01K8V8GHVQ90RYQRJQKEF3Q9AZ",
"name": "Alex Morgan",
"email": "[email protected]",
"phone": null,
"company": "Example Co",
"external_id": "account-1042",
"attributes": {
"plan": "Business"
},
"tags": [],
"is_anonymous": false,
"source": "api",
"first_seen_at": "2026-10-27T10:00:00+00:00",
"last_seen_at": "2026-10-27T10:00:00+00:00",
"created_at": "2026-10-27T10:00:00+00:00",
"updated_at": "2026-10-27T10:00:00+00:00",
"widget_context": []
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| query | string | Optional. Exact email identity. Supply only one lookup field. | |
| query | phone | string | Optional. Exact phone identity. Supply only one lookup field. |
| query | external_id | string | Optional. Exact external_id identity. Supply only one lookup field. |
GET /customers/{customer}
Return a customer profile with canonical attributes and up to five recent website attribute snapshots.
Permission: customers:read. Success: 200. Response schema: CustomerResponse.
curl -X GET "https://trucom.app/api/v1/rest/customers/01K8V8GHVQ90RYQRJQKEF3Q9AZ" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json"{
"data": {
"id": "01K8V8GHVQ90RYQRJQKEF3Q9AZ",
"name": "Alex Morgan",
"email": "[email protected]",
"phone": null,
"company": "Example Co",
"external_id": "account-1042",
"attributes": {
"plan": "Business"
},
"tags": [],
"is_anonymous": false,
"source": "api",
"first_seen_at": "2026-10-27T10:00:00+00:00",
"last_seen_at": "2026-10-27T10:00:00+00:00",
"created_at": "2026-10-27T10:00:00+00:00",
"updated_at": "2026-10-27T10:00:00+00:00",
"widget_context": []
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| path | customer | string | Required. Public ULID of a resource in the key’s workspace. |
POST /customers
Create a profile with at least one of name, email, phone or external_id. Identities must not already belong to another customer. An Idempotency-Key is required.
Permission: customers:write. Success: 201. Response schema: CustomerResponse.
curl -X POST "https://trucom.app/api/v1/rest/customers" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: account-1042-profile-v3" \
-d '{"external_id":"account-1042","name":"Alex Morgan","email":"[email protected]","company":"Example Co","attributes":{"plan":"Business"}}'{
"data": {
"id": "01K8V8GHVQ90RYQRJQKEF3Q9AZ",
"name": "Alex Morgan",
"email": "[email protected]",
"phone": null,
"company": "Example Co",
"external_id": "account-1042",
"attributes": {
"plan": "Business"
},
"tags": [],
"is_anonymous": false,
"source": "api",
"first_seen_at": "2026-10-27T10:00:00+00:00",
"last_seen_at": "2026-10-27T10:00:00+00:00",
"created_at": "2026-10-27T10:00:00+00:00",
"updated_at": "2026-10-27T10:00:00+00:00",
"widget_context": []
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| header | Idempotency-Key | string | Required. Unique operation key. Same method, path and JSON content replays for 24 hours by default. Different content returns 409. Rotation clears replay history. |
| body | name | string, nullable | Optional. Max 160 characters. Display name. |
| body | string, nullable | Optional. Max 255 characters. Primary email; must be valid RFC email syntax. | |
| body | phone | string, nullable | Optional. Max 40 characters. Primary phone; formatting is normalized for identity matching. |
| body | company | string, nullable | Optional. Max 160 characters. Company name. |
| body | external_id | string, nullable | Optional. Max 160 characters. Stable application account identity. |
| body | attributes | object | Optional. Flat attributes; merges by key. Null removes a key. Total stored attributes: 50 keys / 20 KB. prototype, constructor and __proto__ are reserved. |
PUT /customers
external_id is required and must be non-empty. Create a profile if this normalized external ID is new, otherwise update the existing profile. Omitted fields stay unchanged. A conflicting email or phone returns 422; profiles are never merged implicitly.
Permission: customers:write. Success: 201, 200. Response schema: CustomerResponse.
curl -X PUT "https://trucom.app/api/v1/rest/customers" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: account-1042-profile-v3" \
-d '{"external_id":"account-1042","name":"Alex Morgan","email":"[email protected]","company":"Example Co","attributes":{"plan":"Business"}}'{
"data": {
"id": "01K8V8GHVQ90RYQRJQKEF3Q9AZ",
"name": "Alex Morgan",
"email": "[email protected]",
"phone": null,
"company": "Example Co",
"external_id": "account-1042",
"attributes": {
"plan": "Business"
},
"tags": [],
"is_anonymous": false,
"source": "api",
"first_seen_at": "2026-10-27T10:00:00+00:00",
"last_seen_at": "2026-10-27T10:00:00+00:00",
"created_at": "2026-10-27T10:00:00+00:00",
"updated_at": "2026-10-27T10:00:00+00:00",
"widget_context": []
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| header | Idempotency-Key | string | Optional. Unique operation key. Same method, path and JSON content replays for 24 hours by default. Different content returns 409. Rotation clears replay history. |
| body | name | string, nullable | Optional. Max 160 characters. Display name. |
| body | string, nullable | Optional. Max 255 characters. Primary email; must be valid RFC email syntax. | |
| body | phone | string, nullable | Optional. Max 40 characters. Primary phone; formatting is normalized for identity matching. |
| body | company | string, nullable | Optional. Max 160 characters. Company name. |
| body | external_id | string | Required. Max 160 characters. Stable application account identity. |
| body | attributes | object | Optional. Flat attributes; merges by key. Null removes a key. Total stored attributes: 50 keys / 20 KB. prototype, constructor and __proto__ are reserved. |
PATCH /customers/{customer}
Update only supplied fields. Nullable profile fields clear their current values. Attributes merge by key; a null attribute removes the key. Identity conflicts return 422.
Permission: customers:write. Success: 200. Response schema: CustomerResponse.
curl -X PATCH "https://trucom.app/api/v1/rest/customers/01K8V8GHVQ90RYQRJQKEF3Q9AZ" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: account-1042-profile-v3" \
-d '{"attributes":{"plan":"Business"}}'{
"data": {
"id": "01K8V8GHVQ90RYQRJQKEF3Q9AZ",
"name": "Alex Morgan",
"email": "[email protected]",
"phone": null,
"company": "Example Co",
"external_id": "account-1042",
"attributes": {
"plan": "Business"
},
"tags": [],
"is_anonymous": false,
"source": "api",
"first_seen_at": "2026-10-27T10:00:00+00:00",
"last_seen_at": "2026-10-27T10:00:00+00:00",
"created_at": "2026-10-27T10:00:00+00:00",
"updated_at": "2026-10-27T10:00:00+00:00",
"widget_context": []
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| path | customer | string | Required. Public ULID of a resource in the key’s workspace. |
| header | Idempotency-Key | string | Optional. Unique operation key. Same method, path and JSON content replays for 24 hours by default. Different content returns 409. Rotation clears replay history. |
| body | name | string, nullable | Optional. Max 160 characters. Display name. |
| body | string, nullable | Optional. Max 255 characters. Primary email; must be valid RFC email syntax. | |
| body | phone | string, nullable | Optional. Max 40 characters. Primary phone; formatting is normalized for identity matching. |
| body | company | string, nullable | Optional. Max 160 characters. Company name. |
| body | external_id | string, nullable | Optional. Max 160 characters. Stable application account identity. |
| body | attributes | object | Optional. Flat attributes; merges by key. Null removes a key. Total stored attributes: 50 keys / 20 KB. prototype, constructor and __proto__ are reserved. |
GET /customers/{customer}/conversations
Read conversations for this customer in the current workspace.
Permission: conversations:read. Success: 200. Response schema: ConversationListResponse.
curl -X GET "https://trucom.app/api/v1/rest/customers/01K8V8GHVQ90RYQRJQKEF3Q9AZ/conversations?per_page=25" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json"{
"data": [
{
"id": "01K8V8GHVQ90RYQRJQKEF3Q9B0",
"customer_id": "01K8V8GHVQ90RYQRJQKEF3Q9AZ",
"subject": "Help with my order",
"status": "open",
"priority": "normal",
"channel": "live_chat",
"origin": "widget",
"created_at": "2026-10-27T10:00:00+00:00",
"updated_at": "2026-10-27T10:04:00+00:00"
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. Maximum records per page. |
| query | cursor | string | Optional. Use meta.pagination.next_cursor unchanged. |
| path | customer | string | Required. Public ULID of a resource in the key’s workspace. |
GET /conversations
Read conversation summaries in creation order. Filter by a customer public ID or a workspace status value.
Permission: conversations:read. Success: 200. Response schema: ConversationListResponse.
curl -X GET "https://trucom.app/api/v1/rest/conversations?per_page=25" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json"{
"data": [
{
"id": "01K8V8GHVQ90RYQRJQKEF3Q9B0",
"customer_id": "01K8V8GHVQ90RYQRJQKEF3Q9AZ",
"subject": "Help with my order",
"status": "open",
"priority": "normal",
"channel": "live_chat",
"origin": "widget",
"created_at": "2026-10-27T10:00:00+00:00",
"updated_at": "2026-10-27T10:04:00+00:00"
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. Maximum records per page. |
| query | cursor | string | Optional. Use meta.pagination.next_cursor unchanged. |
| query | customer_id | string | Optional. Filter by a customer public ULID. |
| query | status | string | Optional. Exact status value, including workspace custom statuses. |
GET /conversations/{conversation}
Read a conversation summary. Internal metadata, credentials and staff notes are not returned.
Permission: conversations:read. Success: 200. Response schema: ConversationResponse.
curl -X GET "https://trucom.app/api/v1/rest/conversations/01K8V8GHVQ90RYQRJQKEF3Q9B0" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json"{
"data": {
"id": "01K8V8GHVQ90RYQRJQKEF3Q9B0",
"customer_id": "01K8V8GHVQ90RYQRJQKEF3Q9AZ",
"subject": "Help with my order",
"status": "open",
"priority": "normal",
"channel": "live_chat",
"origin": "widget",
"created_at": "2026-10-27T10:00:00+00:00",
"updated_at": "2026-10-27T10:04:00+00:00"
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| path | conversation | string | Required. Public ULID of a resource in the key’s workspace. |
GET /conversations/{conversation}/messages
Read public messages in creation order, oldest first. Internal notes, system events and deleted messages are excluded. attachment_count describes attachments; this endpoint does not return file download URLs.
Permission: conversations:read. Success: 200. Response schema: MessageListResponse.
curl -X GET "https://trucom.app/api/v1/rest/conversations/01K8V8GHVQ90RYQRJQKEF3Q9B0/messages?per_page=25" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json"{
"data": [
{
"id": "01K8V8GHVQ90RYQRJQKEF3Q9B1",
"body": "Can you help me check my order?",
"sender": {
"type": "customer",
"name": "Alex Morgan"
},
"attachment_count": 0,
"sent_at": "2026-10-27T10:04:00+00:00",
"delivered_at": null,
"read_at": null,
"created_at": "2026-10-27T10:04:00+00:00"
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. Maximum records per page. |
| query | cursor | string | Optional. Use meta.pagination.next_cursor unchanged. |
| path | conversation | string | Required. Public ULID of a resource in the key’s workspace. |
POST /widget/identity-tokens
Issue a signed token for the widget this API key belongs to. Configure the widget signing secret first. subject is bound permanently to the selected customer; attempting to reuse it for a different customer returns 409. Derive both subject and customer_id on your trusted backend from its authenticated user.
Permission: widget:identify. Success: 200. Response schema: IdentityTokenResponse.
curl -X POST "https://trucom.app/api/v1/rest/widget/identity-tokens" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Accept: application/json" \
-H "Content-Type: application/json" \
-d '{"customer_id":"01K8V8GHVQ90RYQRJQKEF3Q9AZ","subject":"account-1042","ttl_seconds":900}'{
"data": {
"identity_token": "tcid1.EXAMPLE_PAYLOAD.EXAMPLE_SIGNATURE",
"expires_at": "2026-10-27T10:15:00+00:00"
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| body | customer_id | string | Required. Max 26 characters. |
| body | subject | string | Required. Stable authenticated application user ID, chosen on your server. Case-sensitive and permanently bound to this customer for this widget. Max 160 characters. |
| body | ttl_seconds | integer | Optional integer from 60 to 3,600. Default: 900. |
Customer response fields
| Field | Type | Details |
|---|---|---|
| id | string | Public customer ULID. |
| name | string, nullable | Customer’s display name, or null. |
| string, nullable | Primary email address, or null. | |
| phone | string, nullable | Primary phone number, or null. |
| company | string, nullable | Company name, or null. |
| external_id | string, nullable | Primary external identity from your application, or null. |
| attributes | object | Canonical customer attribute object. Updated by key; website context is separate. |
| tags | array | Array of tag names already assigned in the workspace. |
| is_anonymous | boolean | Whether the profile currently has no identifying details. |
| source | string | How this customer profile was first created. |
| first_seen_at | string, nullable | ISO 8601 timestamp; null when this event has not occurred. |
| last_seen_at | string, nullable | ISO 8601 timestamp; null when this event has not occurred. |
| created_at | string, nullable | ISO 8601 timestamp; null when this event has not occurred. |
| updated_at | string, nullable | ISO 8601 timestamp; null when this event has not occurred. |
| widget_context | array | Show, lookup and write responses only: up to five website attribute snapshots, each with attributes, source and updated_at. |
Conversation response fields
| Field | Type | Details |
|---|---|---|
| id | string | Public conversation ULID. |
| customer_id | string, nullable | Public customer ULID. |
| subject | string, nullable | Conversation subject, or null. |
| status | string | Exact workspace status value, including custom statuses. |
| priority | string | Exact workspace priority value. |
| channel | string | Communication channel, such as live_chat or whatsapp. |
| origin | string | How the conversation began, such as widget, api, agent or integration. |
| created_at | string | ISO 8601 timestamp; null when this event has not occurred. |
| updated_at | string | ISO 8601 timestamp; null when this event has not occurred. |
Message response fields
| Field | Type | Details |
|---|---|---|
| id | string | Public message ULID. |
| body | string, nullable | Public message text. Render as untrusted text. |
| sender | object | Object with type (customer, user, ai or system) and display name (string or null). |
| attachment_count | integer | Number of files attached to this message. No download URLs are returned. |
| sent_at | string, nullable | ISO 8601 timestamp; null when this event has not occurred. |
| delivered_at | string, nullable | ISO 8601 timestamp; null when this event has not occurred. |
| read_at | string, nullable | ISO 8601 timestamp; null when this event has not occurred. |
| created_at | string, nullable | ISO 8601 timestamp; null when this event has not occurred. |
Identity token response fields
| Field | Type | Details |
|---|---|---|
| identity_token | string | Short-lived tcid1 signed proof. Give it only to the authenticated customer. |
| expires_at | string | ISO 8601 expiry. Request a fresh proof after expiry. |
Response headers
| Header | Meaning |
|---|---|
| X-Request-Id | Unique request identifier; available on success and errors. |
| X-RateLimit-Limit | Configured per-key requests per minute on successful responses. |
| X-RateLimit-Remaining | Requests remaining in the current window on successful responses. |
| Retry-After | Seconds until retry on a 429 response. |
| Idempotency-Replayed | true when a successful customer write was replayed. |
| Cache-Control | private, no-store. |
GET /tickets
Workspace tickets, optionally filtered by customer or status.
Permission: tickets:read. Success: 200. Response: TicketListResponse.
curl -X GET "https://trucom.app/api/v1/rest/tickets" \
-H "Authorization: Bearer $TRUCOM_API_KEY"{
"data": [
{
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"reference": "#1042",
"customer_id": "01k8v8ghvq90ryqrjqkef3q9az",
"title": "Please check my delivery",
"description": "The delivery has not arrived.",
"status": "open",
"priority": "normal",
"source": "api",
"department": null,
"created_at": "2026-10-27T12:00:00+00:00",
"updated_at": "2026-10-27T12:00:00+00:00"
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. |
| query | cursor | string | Optional. |
| query | customer_id | string | Optional. |
| query | status | string | Optional. |
GET /customers/{customer}/tickets
List customer tickets.
Permission: tickets:read. Success: 200. Response: TicketListResponse.
curl -X GET "https://trucom.app/api/v1/rest/customers/01k8v8ghvq90ryqrjqkef3q9az/tickets" \
-H "Authorization: Bearer $TRUCOM_API_KEY"{
"data": [
{
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"reference": "#1042",
"customer_id": "01k8v8ghvq90ryqrjqkef3q9az",
"title": "Please check my delivery",
"description": "The delivery has not arrived.",
"status": "open",
"priority": "normal",
"source": "api",
"department": null,
"created_at": "2026-10-27T12:00:00+00:00",
"updated_at": "2026-10-27T12:00:00+00:00"
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. |
| query | cursor | string | Optional. |
| query | status | string | Optional. |
| path | customer | string | Required. |
GET /tickets/{ticket}
Public-facing fields only. Internal notes and service target snapshots are excluded.
Permission: tickets:read. Success: 200. Response: TicketResponse.
curl -X GET "https://trucom.app/api/v1/rest/tickets/01k8v8ghvq90ryqrjqkef3q9b0" \
-H "Authorization: Bearer $TRUCOM_API_KEY"{
"data": {
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"reference": "#1042",
"customer_id": "01k8v8ghvq90ryqrjqkef3q9az",
"title": "Please check my delivery",
"description": "The delivery has not arrived.",
"status": "open",
"priority": "normal",
"source": "api",
"department": null,
"created_at": "2026-10-27T12:00:00+00:00",
"updated_at": "2026-10-27T12:00:00+00:00"
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| path | ticket | string | Required. |
POST /tickets
Create an open API ticket through the normal workspace workflow, billing limits and notifications.
Permission: tickets:write. Success: 201. Response: TicketResponse.
curl -X POST "https://trucom.app/api/v1/rest/tickets" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: support-operation-1042" \
-d '{"customer_id":"01k8v8ghvq90ryqrjqkef3q9az","title":"Please check my delivery","description":"The delivery has not arrived."}'{
"data": {
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"reference": "#1042",
"customer_id": "01k8v8ghvq90ryqrjqkef3q9az",
"title": "Please check my delivery",
"description": "The delivery has not arrived.",
"status": "open",
"priority": "normal",
"source": "api",
"department": null,
"created_at": "2026-10-27T12:00:00+00:00",
"updated_at": "2026-10-27T12:00:00+00:00"
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| header | Idempotency-Key | string | Required. |
| body | customer_id | string | Required. Maximum 26 characters. |
| body | title | string | Required. Maximum 180 characters. |
| body | description | string, nullable | Optional. Maximum 10000 characters. |
| body | priority | string | Optional. |
| body | department_id | string, nullable | Optional. Maximum 26 characters. |
GET /tickets/{ticket}/replies
Public replies only. Attachment counts are returned without file download URLs.
Permission: tickets:read. Success: 200. Response: TicketReplyListResponse.
curl -X GET "https://trucom.app/api/v1/rest/tickets/01k8v8ghvq90ryqrjqkef3q9b0/replies" \
-H "Authorization: Bearer $TRUCOM_API_KEY"{
"data": [
{
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"body": "My order reference is ORD-1042.",
"sender": {
"type": "customer",
"name": "Alex Morgan"
},
"attachment_count": 0,
"sent_at": "2026-10-27T12:00:00+00:00"
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. |
| query | cursor | string | Optional. |
| path | ticket | string | Required. |
POST /tickets/{ticket}/replies
The customer must own the ticket. Closed tickets reject replies with 422. Text-only JSON request.
Permission: tickets:write. Success: 201. Response: TicketReplyResponse.
curl -X POST "https://trucom.app/api/v1/rest/tickets/01k8v8ghvq90ryqrjqkef3q9b0/replies" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: support-operation-1042" \
-d '{"customer_id":"01k8v8ghvq90ryqrjqkef3q9az","body":"My order reference is ORD-1042."}'{
"data": {
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"body": "My order reference is ORD-1042.",
"sender": {
"type": "customer",
"name": "Alex Morgan"
},
"attachment_count": 0,
"sent_at": "2026-10-27T12:00:00+00:00"
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| path | ticket | string | Required. |
| header | Idempotency-Key | string | Required. |
| body | customer_id | string | Required. Maximum 26 characters. |
| body | body | string | Required. Maximum 10000 characters. |
GET /feature-request-boards
List feature request boards.
Permission: feature_requests:read. Success: 200. Response: FeatureRequestBoardListResponse.
curl -X GET "https://trucom.app/api/v1/rest/feature-request-boards" \
-H "Authorization: Bearer $TRUCOM_API_KEY"{
"data": [
{
"id": "01k8v8ghvq90ryqrjqkef3q9b1",
"name": "Product ideas",
"description": "Ideas from our customers.",
"is_public": true,
"accepts_submissions": true,
"is_default": true
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. |
| query | cursor | string | Optional. |
GET /feature-requests
visibility=public returns visible requests on public boards. Other reads are workspace-scoped and must be authorized by the integrating backend.
Permission: feature_requests:read. Success: 200. Response: FeatureRequestListResponse.
curl -X GET "https://trucom.app/api/v1/rest/feature-requests" \
-H "Authorization: Bearer $TRUCOM_API_KEY"{
"data": [
{
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"reference": "FR-1042",
"customer_id": "01k8v8ghvq90ryqrjqkef3q9az",
"board": {
"id": "01k8v8ghvq90ryqrjqkef3q9b1",
"name": "Product ideas"
},
"title": "Scheduled exports",
"description": "We need a weekly report for our team.",
"status": "planned",
"visibility": "public",
"vote_count": 0,
"created_at": "2026-10-27T12:00:00+00:00",
"updated_at": "2026-10-27T12:00:00+00:00"
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. |
| query | cursor | string | Optional. |
| query | customer_id | string | Optional. |
| query | board_id | string | Optional. |
| query | status | string | Optional. |
| query | visibility | string | Optional. |
GET /customers/{customer}/feature-requests
List customer feature requests.
Permission: feature_requests:read. Success: 200. Response: FeatureRequestListResponse.
curl -X GET "https://trucom.app/api/v1/rest/customers/01k8v8ghvq90ryqrjqkef3q9az/feature-requests" \
-H "Authorization: Bearer $TRUCOM_API_KEY"{
"data": [
{
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"reference": "FR-1042",
"customer_id": "01k8v8ghvq90ryqrjqkef3q9az",
"board": {
"id": "01k8v8ghvq90ryqrjqkef3q9b1",
"name": "Product ideas"
},
"title": "Scheduled exports",
"description": "We need a weekly report for our team.",
"status": "planned",
"visibility": "public",
"vote_count": 0,
"created_at": "2026-10-27T12:00:00+00:00",
"updated_at": "2026-10-27T12:00:00+00:00"
}
],
"meta": {
"pagination": {
"per_page": 25,
"next_cursor": null,
"has_more": false
}
}
}| Location | Field | Type | Details |
|---|---|---|---|
| query | per_page | integer | Optional. |
| query | cursor | string | Optional. |
| query | board_id | string | Optional. |
| query | status | string | Optional. |
| query | visibility | string | Optional. |
| path | customer | string | Required. |
GET /feature-requests/{featureRequest}
Get a feature request.
Permission: feature_requests:read. Success: 200. Response: FeatureRequestResponse.
curl -X GET "https://trucom.app/api/v1/rest/feature-requests/01k8v8ghvq90ryqrjqkef3q9b0" \
-H "Authorization: Bearer $TRUCOM_API_KEY"{
"data": {
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"reference": "FR-1042",
"customer_id": "01k8v8ghvq90ryqrjqkef3q9az",
"board": {
"id": "01k8v8ghvq90ryqrjqkef3q9b1",
"name": "Product ideas"
},
"title": "Scheduled exports",
"description": "We need a weekly report for our team.",
"status": "new",
"visibility": "private",
"vote_count": 0,
"created_at": "2026-10-27T12:00:00+00:00",
"updated_at": "2026-10-27T12:00:00+00:00"
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| path | featureRequest | string | Required. |
POST /feature-requests
New, private, source api. The workspace team reviews and publishes requests through the normal workflow.
Permission: feature_requests:write. Success: 201. Response: FeatureRequestResponse.
curl -X POST "https://trucom.app/api/v1/rest/feature-requests" \
-H "Authorization: Bearer $TRUCOM_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: support-operation-1042" \
-d '{"customer_id":"01k8v8ghvq90ryqrjqkef3q9az","title":"Scheduled exports","description":"We need a weekly report for our team."}'{
"data": {
"id": "01k8v8ghvq90ryqrjqkef3q9b0",
"reference": "FR-1042",
"customer_id": "01k8v8ghvq90ryqrjqkef3q9az",
"board": {
"id": "01k8v8ghvq90ryqrjqkef3q9b1",
"name": "Product ideas"
},
"title": "Scheduled exports",
"description": "We need a weekly report for our team.",
"status": "new",
"visibility": "private",
"vote_count": 0,
"created_at": "2026-10-27T12:00:00+00:00",
"updated_at": "2026-10-27T12:00:00+00:00"
},
"meta": []
}| Location | Field | Type | Details |
|---|---|---|---|
| header | Idempotency-Key | string | Required. |
| body | customer_id | string | Required. Maximum 26 characters. |
| body | board_id | string, nullable | Optional. Maximum 26 characters. |
| body | title | string | Required. Maximum 180 characters. |
| body | description | string | Required. Maximum 10000 characters. |