Skip to content

A contact's consent history

GET
/v1/contacts/{id}/consent-history
curl --request GET \
--url https://api.threadkite.app/v1/contacts/2489E9AD-2EE2-8E00-8EC9-32D5F69181C0/consent-history \
--header 'Authorization: Bearer <token>'

Every change to their consent on every channel, and every confirmation of it, newest first: who or what made it, when, how, and the wording they saw. Includes the history of contacts merged into this one. Proof of consent for UK and EU GDPR and PECR.

id
required
string format: uuid
Media typeapplication/json
object
contactId
required
string format: uuid
events
required
Array<object>
object
id
required
string format: uuid
contactId
required

The contact it was recorded for: this contact, or one merged into it (its history is part of this one)

string format: uuid
recordedForName
required

The name of the merged contact it was recorded for; null when it was recorded for this contact

string
nullable
channel
required

email, sms, whatsapp or phone

string
purpose
required
string
Allowed values: marketing service reminders
state
required

The decision after it. pending_opt_in: an opt-in from someone we could not verify for a contact who had opted out, kept but not applied

string
Allowed values: opted_in opted_out unknown pending_opt_in
previousState
required
string
Allowed values: opted_in opted_out unknown pending_opt_in
source
required

Who or what made it

string
Allowed values: staff api_key contact_form assistant_chat inbound_keyword unsubscribe_link import connection_sync email_complaint provider_opt_out merge merge_undone system
summary
required

What happened, in plain English

string
at
required

When the decision was made

string format: date-time
recordedAt
required

When Threadkite recorded it

string format: date-time
userId
required

The team member who made it

string
nullable
userName
required

Their name, unless they have left

string
nullable
apiKeyId
required
string format: uuid
nullable
apiKeyName
required

The API key’s name, unless it was deleted

string
nullable
formId
required
string format: uuid
nullable
formName
required
string
nullable
formSubmissionId
required
string format: uuid
nullable
messageId
required

The message behind it (the STOP text, the form lead, the email complained about)

string format: uuid
nullable
connectionId
required
string format: uuid
nullable
connectionName
required
string
nullable
assistantChatId
required
string format: uuid
nullable
mergeId
required
string format: uuid
nullable
relatedContactId
required

For merges: the other contact

string format: uuid
nullable
relatedContactName
required
string
nullable
keyword
required

The word they sent

string
nullable
wording
required

The consent wording shown, exactly, with the boxes ticked ([x]) and not ([ ])

string
nullable
wordingVersion
required

A version or hash that pins the wording

string
nullable
pageUrl
required

The page the form was on

string
nullable
ipHash
required

A keyed hash of the network it came from (never the address)

string
nullable
note
required

Anything else kept with it

string
nullable

Example

{
"events": [
{
"recordedForName": null,
"channel": "sms",
"purpose": "marketing",
"state": "opted_out",
"previousState": "opted_in",
"source": "inbound_keyword",
"summary": "Opted out by replying STOP to a text",
"formName": "Leeds website",
"keyword": "STOP"
}
]
}

Missing or invalid API key

Media typeapplication/json
object
statusCode
required
number
code
required

Stable machine-readable reason

string
message
required
string
errors

With code invalid: every problem with the request, by field (message is the first)

Array<object>
object
path
required

Dotted path inside the item, e.g. attributes.price.amountMinor

string
message
required
string

Example

{
"statusCode": 403,
"code": "forbidden",
"message": "You do not have permission to do that.",
"errors": [
{
"message": "Enter the make"
}
]
}

The organisation is on the Free plan (code upgrade_required)

Media typeapplication/json
object
statusCode
required
number
code
required

Stable machine-readable reason

string
message
required
string
feature
required

The feature that needs Pro

string
nullable
Allowed values: extraSeats connections aiAssistant aiReplies rules fullReports api inboxes bulkMessages videoMessages
upgradePath
required

Where to upgrade or pay, in the web app

string

Example

{
"statusCode": 402,
"code": "upgrade_required",
"message": "Connections are part of Pro. Upgrade to connect texts, calls and more.",
"feature": "extraSeats",
"upgradePath": "/settings/billing"
}

The key does not have the scope (or the person the permission)

Media typeapplication/json
object
statusCode
required
number
code
required

Stable machine-readable reason

string
message
required
string
errors

With code invalid: every problem with the request, by field (message is the first)

Array<object>
object
path
required

Dotted path inside the item, e.g. attributes.price.amountMinor

string
message
required
string

Example

{
"statusCode": 403,
"code": "forbidden",
"message": "You do not have permission to do that.",
"errors": [
{
"message": "Enter the make"
}
]
}
Media typeapplication/json
object
statusCode
required
number
code
required

Stable machine-readable reason

string
message
required
string
errors

With code invalid: every problem with the request, by field (message is the first)

Array<object>
object
path
required

Dotted path inside the item, e.g. attributes.price.amountMinor

string
message
required
string

Example

{
"statusCode": 403,
"code": "forbidden",
"message": "You do not have permission to do that.",
"errors": [
{
"message": "Enter the make"
}
]
}

Rate limit reached

Media typeapplication/json
object
statusCode
required
number
code
required

Stable machine-readable reason

string
message
required
string
retryAfter
required

Seconds until another request will be accepted

number

Example

{
"statusCode": 429,
"code": "rate_limited",
"message": "Too many requests. Each key can make 120 requests a minute; try again in 12 seconds.",
"retryAfter": 12
}