Only show these results:

Message tracking

The Nylas API offers several ways to track different types of actions that may happen to a message or thread. You can track:

  • Links clicked
  • Message opened
  • Thread replied

Nylas sends a webhook notification to your server when these actions occur. If you haven't set up webhooks yet, review our webhooks documentation. Make sure you enable the triggers you want to be notified about from your developer dashboard before you send a message with tracking enabled.

ℹ️ Email Analytics is available for Core and Plus plans. Not available for Calendar-only plans.

Nylas detects an email has been read by embedding an image pixel into the message HTML. The image pixel needs to be downloaded for Nylas to detect that the message was opened. Only the initial download is tracked.

There are three different ways you can track a message or thread, and you can use any combination of these tracking features. All you have to do is include a tracking attribute when you send a message through the /send endpoint.

How message tracking works

Once a user acts on a message that you've enabled tracking for (e.g., opening the message), Nylas will make a POST request to your webhook endpoint, with delta information about the action that occurred.

The object_data will contain a metadata sub-attribute that has information about the action. To see the more general structure of the webhook notification, see Webhooks

Enabling tracking

To enable tracking for a message, include a tracking attribute with the other attributes when you send a message. You can include the tracking object when you send a draft or when you send a message directly.

The Tracking object

Attribute Type Description
links boolean True enables link tracking.
opens boolean True enables message open tracking.
thread_replies boolean True enables thread reply tracking.
payload string An optional string that allows you to keep track of additional information. This string will be included in the webhook notification.
 curl -X POST -H "Authorization: Basic <access_token>" -d '{
"reply_to_message_id": "84umizq7c4jtrew491brpa6iu",
"body" : "Please click this: <a href='https://nylas.com/'>click</a>",
"subject": "New Site",
"to": [
{
"name": "Nylas",
"email": "[email protected]"
}
],
"tracking": {
"links": true,
"opens": true,
"thread_replies": false,
"payload": "Any string you want!!"
}
}'
"https://api.nylas.com/send"
from nylas import APIClient

# Initialize and connect to the Nylas client
nylas = APIClient(
CLIENT_ID,
CLIENT_SECRET,
ACCESS_TOKEN
)

# If the draft has not been created
# Create a draft with a tracking object
draft = nylas.drafts.create()
draft.subject = "With Love, from Nylas"
draft.body = "This email was sent using the Nylas Email API. Visit https://nylas.com for details."
draft.to = [{'name': 'Me', 'email': '[email protected]'}]
draft.tracking = {"links": 'true', "opens": 'true', "thread_replies": 'true', "payload": "payload"}

# Send the draft
draft.send()

# Or, if the draft already exists
# Just add the tracking object to the existing draft object
draft = nylas.drafts.get(draft.id)
draft.tracking = {"links": 'true', "opens": 'true', "thread_replies": 'true', "payload": "payload"}

# Send the draft
draft.send()
import com.nylas.NylasClient;
import com.nylas.NylasAccount;
import com.nylas.Tracking;
import com.nylas.Draft;
import com.nylas.NameEmail;
import java.util.Arrays;

public class NylasExamples {
public static void messageTrackingExample() throws Exception {
// Initialize and connect to the Nylas client
NylasClient nylas = new NylasClient();
NylasAccount account = nylas.account("ACCESS_TOKEN");

// If the draft has not been created
Draft draft = new Draft();
draft.setSubject("With Love, From Nylas");
draft.setTo(Arrays.asList(new NameEmail("Nylas", "[email protected]")));
draft.setBody("This email was sent using the Nylas email API. Visit https://nylas.com for details.");

// Create the tracking object and add it to the draft
Tracking tracking = new Tracking();
tracking.setOpens(true);
tracking.setLinks(true);
tracking.setThreadReplies(true);
tracking.setPayload("payload");
draft.setTracking(tracking);

// Send the draft
account.drafts().send(draft);

// Or, if the draft already exists
// Just add the tracking object to the existing draft object
Draft draft = account.drafts().get("draft-id");
draft.setTracking(tracking);

// Send the draft
account.drafts().send(draft);
}
}
const Nylas = require('nylas');
const { default: Draft } = require('nylas/lib/models/draft');

// Initialize and connect to the Nylas client
Nylas.config({
clientId: CLIENT_ID,
clientSecret: CLIENT_SECRET
});
const nylas = Nylas.with(ACCESS_TOKEN);

// If the draft has not been created
let draft = new Draft(nylas, {
subject: 'With Love, from Nylas',
to: [{ name: 'Nylas', email: '[email protected]' }],
body: 'This email was sent using the Nylas email API. Visit https://nylas.com for details.'
});

// Create the tracking object
const tracking = { "links": true, "opens": true, "thread_replies": true, "payload": "payload" };

// Send the new draft with the tracking object passed in as an argument
draft.send(tracking).then(message => {
console.log(`${message.id} was sent`);
});

// Or, if the draft already exists
draft = nylas.drafts.find('draft-id');

// Send the existing draft with the tracking object passed in as an argument
draft.send(tracking).then(message => {
console.log(`${message.id} was sent`);
});

#!/usr/bin/env ruby
require 'nylas'

# Initialize and connect to the Nylas client
nylas = Nylas::API.new(
app_id: CLIENT_ID,
app_secret: CLIENT_SECRET,
access_token: ACCESS_TOKEN
)

# If the draft has not been created
# Create a draft with a tracking object
draft = nylas.drafts.create(
to: [{ email: '[email protected]', name: "Nylas" }],
subject: 'With Love, from Nylas',
body: 'This email was sent using the Nylas email API. Visit https://nylas.com for details.',
tracking: { "links": true, "opens": true, "thread_replies": true }
)

# Send the draft
draft.send!

# Or, if the draft already exists
# Just add the tracking object to the existing draft object
draft = nylas.drafts.find('draft-id')
draft.tracking = { "links": true, "opens": true, "thread_replies": true, "payload": "payload" }

# Send the draft
draft.send!

When you send a message with link tracking enabled, Nylas notifies you when a recipient clicks on tracked links in that message.

To enable link tracking for a message, set links to true in the tracking attribute, when sending the message through the /send endpoint.

To set up a link so Nylas can track it, you must use a valid URI scheme and wrap the link in HTML <a></a> tags.

Nylas supports the following URI schemes:

  • http
  • https
  • mailto
  • tel

The link must also be wrapped in HTML <a></a> tags so that Nylas can detect the links to track. Most email clients automatically detect items that look like links, such as 10.0.0.1, tel:5402502334, or apple.com, and render them as clickable, so it's easy to get out of the habit of writing correct HTML. However, links must be formatted with the correct HTML <a></a> tags before you make a request to /send.

The following are examples of valid links that Nylas can detect and track.

  • <a href="https://www.google.com">google.com</a>
  • <a href="mailto:[email protected]">Mailto Nyla!</a>

The examples below are malformed or invalid links that cannot be tracked

  • <a>www.google.com</a>
  • <a href="zoommtg://zoom.us/join?confno=12345">Join a zoom conference</a>

Invalid and malformed links are not replaced with a tracking link, and are left as written.

When link tracking is enabled, Nylas rewrites all valid HTML links with a new URL that allows tracking. This rewrite process prevents tracking links with embedded login credentials, because the destination servers don't recognize the rewritten credentials.

Nylas ignores links that contain credentials. This means that the links still work as expected, however this means that link tracking does not work for these links.

For example, private Google Form URLs contain login credentials, so Nylas ignores the link and it cannot be tracked.

...
"to": [
{
"email": "[email protected]",
"name": "Nylas personal"
}
],
"tracking": {
"links": true,
"opens": true,
"thread_replies": true,
"payload": "Tracking enabled"
},
"subject": "email index"
...
{
"deltas": [
{
"date": 1471630848,
"type": "message.link_clicked",
"object": "metadata",
"object_data": {
"object": "metadata",
"id": "NYLAS_METADATA_ID",
"account_id": "EMAIL_ACCOUNT_ID",
"metadata": {
"sender_app_id": "SENDER_APP_ID",
"link_data": [
{"url": "apple.com", "count": 2},
{"url": "apple.com", "count": 0},
{"url": "nylas.com", "count": 10},
],
"payload": "hello world",
"message_id": "NYLAS_MESSAGE_ID",
"recents": [{
"id:" 0,
"ip": "0.0.0.0",
"user_agent": "chrome",
"link_index": 2
}, ...]
}
}
}
]
}

Learn More

Link tracking metadata.

Recents Array

The recents field contains the last 50 events. These have IDs in order to help parse which events have already been processed. The IDs are only unique within a particular recents array, and there is a separate recents array for each message/trigger pair. For example, opening message A, clicking on a link in message A, and opening message B will all have an id of 0. Opening message A again will have an id of 1.

Errors in Message Tracking

A message with link tracking enabled that has too many links tracked in it may fail to send. If this occurs, disable link tracking to send the message.

The error message returned is:

The message has not been sent. Link tracking cannot be supported for this number of links and/or size of payload. Please try resending with link tracking disabled.

If a message with either Open or Reply tracking cannot handle the metadata object's size in the message, for example, the payload value is too big. If this occurs, disable tracking to send the message. One of the following error messages will be returned:

  • The message has not been sent. Please try resending with open tracking disabled.
  • The message has not been sent. Please try resending with reply tracking disabled.

Open Tracking

When you send a message with open tracking enabled, you will be notified whenever any of the recipients open that message. Opened messages are tracked by embedding 1x1 pixel image in the email. The message.opened webhook is triggered when the image is loaded.

To enable open tracking for a message, set opens to true in the tracking attribute when sending the message through the /send endpoint.

See the webhook information about the Message Opened endpoint

Tip: CDN and caching behavior can change how Message Opened webhooks behave. See Troubleshooting immediate webhook notifications for more information.

Open Tracking Send Example

...
"to": [
{
"email": "[email protected]",
"name": "Nylas personal"
}
],
"tracking": {
"links": true,
"opens": true,
"thread_replies": true,
"payload": "Tracking enabled"
},
"subject": "email index"
...

Open Tracking Response Example

        {
"deltas": [
{
"date": 1471630848,
"type": "message.opened",
"object": "metadata",
"object_data": {
"object": "metadata",
"id": "NYLAS_METADATA_ID",
"account_id": "EMAIL_ACCOUNT_ID",
"metadata": {
"sender_app_id": "SENDER_APP_ID",
"count": "OPEN_COUNT",
"payload": "{myCustom: 'data'}",
"message_id": "NYLAS_MESSAGE_ID",
"recents": [{
"id:" 0,
"ip": "0.0.0.0",
"user_agent": "chrome"
}, ...]
},
}
}
]
}

Thread Replied

When you send a message with reply tracking enabled, you will be notified whenever any corresponding thread participant responds to that thread. To enable reply tracking for a thread, set thread_replies to true in the tracking attribute when sending the message through the /send endpoint.

Thread Replied Send Example

...
"to": [
{
"email": "[email protected]",
"name": "Nylas personal"
}
],
"tracking": {
"links": true,
"opens": true,
"thread_replies": true,
"payload": "Tracking enabled"
},
"subject": "email index"
...

Thread Replied Response Example

 {
"deltas": [
{
"date": 1471630848,
"type": "thread.replied",
"object": "metadata",
"object_data": {
"object": "metadata",
"id": "NYLAS_METADATA_ID",
"account_id": "EMAIL_ACCOUNT_ID",
"metadata": {
"sender_app_id": "SENDER_APP_ID",
"payload": "{myCustom: 'data'}",
"message_id": "NYLAS_MESSAGE_ID",
"reply_to_message_id": "NYLAS_REPLY_TO_MESSAGE_ID",
"thread_id": "NYLAS_THREAD_ID",
"from_self": true,
"timestamp": 1471630848,
},
}
}
]
}

Scopes

You need to enable the email.metadata, as it relies on tracking new messages coming in. Reply tracking cannot be implemented with send-only scope.

View the Nylas Scopes for the complete collection and the Authentication Scopes section for specific dependencies.