Skip to content

People

APIs for managing people (contacts) in your Lindris account.

As a reminder, all requests must be authenticated and use the base URL: https://api.lindris.com

List people

GET api/people

Retrieve a paginated list of people with optional filtering

Query Parameters

  • filter[segments] string optional - Comma-separated list of segment IDs. Prefix with - to exclude. Example: 5,7,-9
  • filter[tags] string optional - List of tag names to filter by. Prefix with - to exclude. Example: my-tag,-unwanted-tag
  • filter[email] string optional - Keywords to filter email addresses. Example: @octeth
  • filter[status] string optional - Filter by subscription status. Example: confirmed
    • Must be one of:
      • unsubscribed
      • confirmed
      • unconfirmed
      • blocked
  • filter[field-{XYZ}] string optional - Filter by custom field value where XYZ is the field name.
    • Example: filter[field-full-name]=John Doe
  • page integer optional - Page number for pagination. Example: 2

Response Fields

  • data[] array
    • id integer optional - The unique identifier for the person
    • email string optional - The person's email address
    • status string optional - The person's active status (active, inactive)
    • statusDetails string optional - Detailed subscription status (confirmed, unconfirmed, unsubscribed, blocked)
    • customFields object optional - Custom field data associated with the person
    • tags string[] optional - List of tags associated with the person
    • timestamp integer optional - Unix timestamp of when the person was created
  • meta array
    • currentPage integer optional - The current page number
    • lastPage integer optional - The last available page number
    • from integer optional - The starting record number on this page
    • to integer optional - The ending record number on this page
    • total integer optional - The total number of matching people
    • perPage integer optional - The number of results per page
    • path string optional - The base URL path for this endpoint
  • links array
    • next string optional - URL for the next page of results, or null if on the last page
    • prev string optional - URL for the previous page of results, or null if on the first page
    • first string optional - URL for the first page of results
    • last string optional - URL for the last page of results

Request

bash
curl --request GET \
    --get "https://api.lindris.com/api/people?filter%5Bsegments%5D=5%2C7%2C-9&filter%5Btags%5D=my-tag%2C-unwanted-tag&filter%5Bemail%5D=%40octeth&filter%5Bstatus%5D=confirmed&filter%5Bfield-%7BXYZ%7D%5D=filter%5Bfield-full-name%5D%3DJohn+Doe&page=2" \
    --header "Authorization: Bearer {YOUR_API_KEY}" \
    --header "Content-Type: application/json"
php
$client = new \GuzzleHttp\Client();
$url = 'https://api.lindris.com/api/people';
$response = $client->get(
    $url,
    [
        'headers' => [
            'Authorization' => 'Bearer {YOUR_API_KEY}',
            'Content-Type' => 'application/json',
        ],
        'query' => [
            'filter[segments]' => '5,7,-9',
            'filter[tags]' => 'my-tag,-unwanted-tag',
            'filter[email]' => '@octeth',
            'filter[status]' => 'confirmed',
            'filter[field-{XYZ}]' => 'filter[field-full-name]=John Doe',
            'page' => '2',
        ],
    ]
);
$body = $response->getBody();
print_r(json_decode((string) $body));
javascript
const url = new URL(
    "https://api.lindris.com/api/people"
);

const params = {
    "filter[segments]": "5,7,-9",
    "filter[tags]": "my-tag,-unwanted-tag",
    "filter[email]": "@octeth",
    "filter[status]": "confirmed",
    "filter[field-{XYZ}]": "filter[field-full-name]=John Doe",
    "page": "2",
};
Object.keys(params)
    .forEach(key => url.searchParams.append(key, params[key]));

const headers = {
    "Authorization": "Bearer {YOUR_API_KEY}",
    "Content-Type": "application/json",
    "Accept": "application/json",
};

fetch(url, {
    method: "GET",
    headers,
}).then(response => response.json());

Response

json
{
   "data": [
      {
         "id": "1",
         "status": "active",
         "statusDetails": "confirmed",
         "email": "[email protected]",
         "customFields": {
            "fullName": "test"
         },
         "tags": null,
         "timestamp": 1702513540
      }
   ],
   "meta": {
      "currentPage": 2,
      "lastPage": 2,
      "from": 11,
      "to": 11,
      "total": 11,
      "perPage": 10,
      "path": "/api/people"
   },
   "links": {
      "next": null,
      "prev": "/api/people?page=1",
      "first": "/api/people?page=1",
      "last": "/api/people?page=2"
   }
}

Check person exists

GET api/people/check/{email}

URL Parameters

Response Fields

  • exists boolean optional - Whether the person exists in your account
  • email string optional - The email address that was checked

Request

bash
curl --request GET \
    --get "https://api.lindris.com/api/people/check/[email protected]" \
    --header "Authorization: Bearer {YOUR_API_KEY}" \
    --header "Content-Type: application/json"
php
$client = new \GuzzleHttp\Client();
$url = 'https://api.lindris.com/api/people/check/[email protected]';
$response = $client->get(
    $url,
    [
        'headers' => [
            'Authorization' => 'Bearer {YOUR_API_KEY}',
            'Content-Type' => 'application/json',
        ],
    ]
);
$body = $response->getBody();
print_r(json_decode((string) $body));
javascript
const url = new URL(
    "https://api.lindris.com/api/people/check/[email protected]"
);

const headers = {
    "Authorization": "Bearer {YOUR_API_KEY}",
    "Content-Type": "application/json",
    "Accept": "application/json",
};

fetch(url, {
    method: "GET",
    headers,
}).then(response => response.json());

Responses

json
{
   "exists": true,
   "email": "[email protected]"
}
json
{
   "exists": false,
   "email": "[email protected]"
}

Get person details

GET api/people/{idOrEmail}

Retrieve a single person by their ID or email address

URL Parameters

Response Fields

  • data array
    • id integer optional - The unique identifier for the person
    • email string optional - The person's email address
    • status string optional - The person's active status (active, inactive)
    • statusDetails string optional - Detailed subscription status (confirmed, unconfirmed, unsubscribed, blocked)
    • customFields object optional - Custom field data associated with the person
    • tags string[] optional - List of tags associated with the person
    • series string[] optional - List of drip series the person is enrolled in
    • timestamp integer optional - Unix timestamp of when the person was created

Request

bash
curl --request GET \
    --get "https://api.lindris.com/api/people/[email protected]" \
    --header "Authorization: Bearer {YOUR_API_KEY}" \
    --header "Content-Type: application/json"
php
$client = new \GuzzleHttp\Client();
$url = 'https://api.lindris.com/api/people/[email protected]';
$response = $client->get(
    $url,
    [
        'headers' => [
            'Authorization' => 'Bearer {YOUR_API_KEY}',
            'Content-Type' => 'application/json',
        ],
    ]
);
$body = $response->getBody();
print_r(json_decode((string) $body));
javascript
const url = new URL(
    "https://api.lindris.com/api/people/[email protected]"
);

const headers = {
    "Authorization": "Bearer {YOUR_API_KEY}",
    "Content-Type": "application/json",
    "Accept": "application/json",
};

fetch(url, {
    method: "GET",
    headers,
}).then(response => response.json());

Responses

json
{
   "data": {
      "id": "1",
      "status": "active",
      "statusDetails": "confirmed",
      "email": "[email protected]",
      "customFields": {
         "fullName": "test"
      },
      "tags": [
         "tagName1",
         "tagName2"
      ],
      "series": [
         {
            "id": "01hsft8kccmm3hmy4nrevxtmft",
            "name": "Welcome Series"
         }
      ],
      "timestamp": 1702513540
   }
}
json
{
   "message": "Person not found"
}

List person events

GET api/people/{idOrEmail}/events

Retrieve a paginated list of events for a person by their ID or email address.

URL Parameters

Query Parameters

  • filter object optional -
    • event string optional - Must not be greater than 100 characters. Example: bxpwlrkoflcs
    • search string optional - Must not be greater than 255 characters. Example: c
    • date_from string optional - Must be a valid date in the format Y-m-d. Example: 2026-04-15
    • date_to string optional - Must be a valid date in the format Y-m-d. Example: 2026-04-15
  • per_page integer optional - Results per page (1–100, default 10). Example: 25

  • page integer optional - Page number for pagination. Example: 1

  • filter[event] string optional - Filter by event type name. Example: pageView

  • filter[search] string optional - Search keyword across event data. Example: checkout

  • filter[date_from] string optional - Start date (YYYY-MM-DD format). Example: 2024-01-01

  • filter[date_to] string optional - End date (YYYY-MM-DD format). Example: 2024-12-31

Response Fields

  • data[] array
    • timestamp integer optional - Unix timestamp of when the event occurred
    • event string optional - The event type name (e.g. pageView, order_completed)
    • properties object optional - Key-value pairs of event-specific data
  • meta array
    • currentPage integer optional - The current page number
    • lastPage integer optional - The last available page number
    • from integer optional - The starting record number on this page
    • to integer optional - The ending record number on this page
    • total integer optional - The total number of matching events
    • perPage integer optional - The number of results per page
    • path string optional - The base URL path for this endpoint
  • links array
    • next string optional - URL for the next page of results, or null if on the last page
    • prev string optional - URL for the previous page of results, or null if on the first page
    • first string optional - URL for the first page of results
    • last string optional - URL for the last page of results

Request

bash
curl --request GET \
    --get "https://api.lindris.com/api/people/[email protected]/events?filter[event]=bxpwlrkoflcs&filter[search]=c&filter[date_from]=2026-04-15&filter[date_to]=2026-04-15&per_page=25&page=1&filter%5Bevent%5D=pageView&filter%5Bsearch%5D=checkout&filter%5Bdate_from%5D=2024-01-01&filter%5Bdate_to%5D=2024-12-31" \
    --header "Authorization: Bearer {YOUR_API_KEY}" \
    --header "Content-Type: application/json"
php
$client = new \GuzzleHttp\Client();
$url = 'https://api.lindris.com/api/people/[email protected]/events';
$response = $client->get(
    $url,
    [
        'headers' => [
            'Authorization' => 'Bearer {YOUR_API_KEY}',
            'Content-Type' => 'application/json',
        ],
        'query' => [
            'filter[event]' => 'bxpwlrkoflcs',
            'filter[search]' => 'c',
            'filter[date_from]' => '2026-04-15',
            'filter[date_to]' => '2026-04-15',
            'per_page' => '25',
            'page' => '1',
            'filter[event]' => 'pageView',
            'filter[search]' => 'checkout',
            'filter[date_from]' => '2024-01-01',
            'filter[date_to]' => '2024-12-31',
        ],
    ]
);
$body = $response->getBody();
print_r(json_decode((string) $body));
javascript
const url = new URL(
    "https://api.lindris.com/api/people/[email protected]/events"
);

const params = {
    "filter[event]": "bxpwlrkoflcs",
    "filter[search]": "c",
    "filter[date_from]": "2026-04-15",
    "filter[date_to]": "2026-04-15",
    "per_page": "25",
    "page": "1",
    "filter[event]": "pageView",
    "filter[search]": "checkout",
    "filter[date_from]": "2024-01-01",
    "filter[date_to]": "2024-12-31",
};
Object.keys(params)
    .forEach(key => url.searchParams.append(key, params[key]));

const headers = {
    "Authorization": "Bearer {YOUR_API_KEY}",
    "Content-Type": "application/json",
    "Accept": "application/json",
};

fetch(url, {
    method: "GET",
    headers,
}).then(response => response.json());

Responses

json
{
   "data": [
      {
         "timestamp": 1718443800,
         "event": "pageView",
         "properties": {
            "$current_url": "https://example.com/shop",
            "$page_title": "Shop"
         }
      },
      {
         "timestamp": 1718440200,
         "event": "order_completed",
         "properties": {
            "order_id": "12345",
            "total": "49.99"
         }
      }
   ],
   "meta": {
      "currentPage": 1,
      "lastPage": 1,
      "from": 1,
      "to": 2,
      "total": 2,
      "perPage": 10,
      "path": "/api/people/[email protected]/events"
   },
   "links": {
      "next": null,
      "prev": null,
      "first": "/api/people/[email protected]/events?page=1",
      "last": "/api/people/[email protected]/events?page=1"
   }
}
json
{
   "message": "Person not found"
}
json
{
   "message": "The filter.date from does not match the format Y-m-d.",
   "errors": {
      "filter.date_from": [
         "The filter.date from does not match the format Y-m-d."
      ]
   },
   "status_code": 422
}

Create or update person

POST api/people

Create a new person or update an existing one

Request Body

  • id integer optional - The person's Lindris ID. Either email or id must be included. Example: 1

  • email string optional - The person's email address. Either email or id must be included.

  • emailChange string optional - Provide this if you need to update the email address of an existing contact. Use with the "email" or "id" field to identify the contact to update. Example: [email protected]

  • source string required - The e-commerce platform source. Example: woocommerce

  • customFields object optional - Custom field data for the person.

    TIP

    The following are Default System Fields available for use:

    • firstName: Person's first name
    • lastName: Person's last name
    • phoneNumber: Phone number (include country code)
    • referenceId: External system reference ID

    Example:

json
{
   "firstName": "John",
   "lastName": "Doe",
   "phoneNumber": "+1234567890",
   "shirtSize": "Medium"
}
  • tags object optional - Tags to add (true) or remove (false). Example:
json
{
   "tagToBeAdded": true,
   "tagToBeRemoved": false
}
  • series object optional - Series IDs to add to (true) or remove from (false). Example:
json
{
   "seriesIdToBeAddedTo": true,
   "seriesIdToBeRemovedFrom": false
}
  • events string[] optional - Events to track for this person. For an in-depth explanation see the documentation. Example:
json
[
   {
      "eventName": "import-completed",
      "method": "csv"
   }
]
  • skipDoubleOptIn boolean optional - When true, bypasses the account's double opt-in setting for this request. The person will be created/updated with the requested status instead of being forced to "Opt-In Pending". No confirmation email will be sent. Useful for importing contacts who have already confirmed their subscription on another platform. Example: true

  • status string optional - The person's active status. This is determined by multiple factors including subscription status, hard bounce status, and suppression list status. A person can only receive emails when 'active'. Example: active

    • Must be one of:
      • active
      • inactive
  • statusDetails string optional - The detailed subscription status of the person. This provides more granular control over the person's state:

    • confirmed: Person is subscribed and can receive emails
    • unconfirmed: Person is pending double opt-in confirmation
    • unsubscribed: Person has explicitly unsubscribed

    Note: Cannot set 'active' status when person is blocked or hard bounced.

    • Must be one of:
      • confirmed
      • unconfirmed
      • unsubscribed

Response Fields

  • data array
    • id integer optional - The unique identifier for the person
    • email string optional - The person's email address
    • status string optional - The person's active status (active,inactive). This is determined by multiple factors including subscription status, hard bounce status, and suppression list status. The person can only receive emails when 'active'.
    • statusDetails string optional - Detailed subscription status of the person. Provides granular state information about the person's subscription state:
      • confirmed: Person is subscribed and can receive emails
      • unconfirmed: Person is pending double opt-in confirmation. When double opt-in is enabled, all new contacts are created with this status.
      • unsubscribed: Person has explicitly unsubscribed
      • blocked: Person is suppressed due to hard bounce or other issues
    • customFields object optional - Custom field data associated with the person
    • tags string[] optional - List of tags associated with the person
    • series string[] optional - List of series the person is enrolled in
    • eventUuid string optional - The UUID of any events tracked for this person in this request.

Request

bash
curl --request POST \
    "https://api.lindris.com/api/people" \
    --header "Authorization: Bearer {YOUR_API_KEY}" \
    --header "Content-Type: application/json" \
    --data "{
    \"id\": 1,
    \"emailChange\": \"[email protected]\",
    \"source\": \"woocommerce\",
    \"customFields\": {
        \"firstName\": \"John\",
        \"lastName\": \"Doe\",
        \"phoneNumber\": \"+1234567890\",
        \"shirtSize\": \"Medium\"
    },
    \"tags\": {
        \"tagToBeAdded\": true,
        \"tagToBeRemoved\": false
    },
    \"series\": {
        \"seriesIdToBeAddedTo\": true,
        \"seriesIdToBeRemovedFrom\": false
    },
    \"events\": [
        {
            \"eventName\": \"import-completed\",
            \"method\": \"csv\"
        }
    ],
    \"skipDoubleOptIn\": true,
    \"status\": \"active\"
}"
php
$client = new \GuzzleHttp\Client();
$url = 'https://api.lindris.com/api/people';
$response = $client->post(
    $url,
    [
        'headers' => [
            'Authorization' => 'Bearer {YOUR_API_KEY}',
            'Content-Type' => 'application/json',
        ],
        'json' => \Symfony\Component\VarExporter\Internal\Hydrator::hydrate(
            $o = [
                clone (\Symfony\Component\VarExporter\Internal\Registry::$prototypes['stdClass'] ?? \Symfony\Component\VarExporter\Internal\Registry::p('stdClass')),
            ],
            null,
            [
                'stdClass' => [
                    'eventName' => [
                        'import-completed',
                    ],
                    'method' => [
                        'csv',
                    ],
                ],
            ],
            [
                'id' => 1,
                'emailChange' => '[email protected]',
                'source' => 'woocommerce',
                'customFields' => [
                    'firstName' => 'John',
                    'lastName' => 'Doe',
                    'phoneNumber' => '+1234567890',
                    'shirtSize' => 'Medium',
                ],
                'tags' => [
                    'tagToBeAdded' => true,
                    'tagToBeRemoved' => false,
                ],
                'series' => [
                    'seriesIdToBeAddedTo' => true,
                    'seriesIdToBeRemovedFrom' => false,
                ],
                'events' => [
                    $o[0],
                ],
                'skipDoubleOptIn' => true,
                'status' => 'active',
            ],
            []
        ),
    ]
);
$body = $response->getBody();
print_r(json_decode((string) $body));
javascript
const url = new URL(
    "https://api.lindris.com/api/people"
);

const headers = {
    "Authorization": "Bearer {YOUR_API_KEY}",
    "Content-Type": "application/json",
    "Accept": "application/json",
};

let body = {
    "id": 1,
    "emailChange": "[email protected]",
    "source": "woocommerce",
    "customFields": {
        "firstName": "John",
        "lastName": "Doe",
        "phoneNumber": "+1234567890",
        "shirtSize": "Medium"
    },
    "tags": {
        "tagToBeAdded": true,
        "tagToBeRemoved": false
    },
    "series": {
        "seriesIdToBeAddedTo": true,
        "seriesIdToBeRemovedFrom": false
    },
    "events": [
        {
            "eventName": "import-completed",
            "method": "csv"
        }
    ],
    "skipDoubleOptIn": true,
    "status": "active"
};

fetch(url, {
    method: "POST",
    headers,
    body: JSON.stringify(body),
}).then(response => response.json());

Responses

json
{
   "data": {
      "id": "1",
      "status": "active",
      "statusDetails": "confirmed",
      "email": "[email protected]",
      "customFields": {
         "fullName": "test"
      },
      "tags": [
         "tagName1",
         "tagName2"
      ],
      "series": [
         {
            "id": "01hsft8kccmm3hmy4nrevxtmft",
            "name": "Welcome Series"
         }
      ],
      "timestamp": 1702513540
   }
}
json
{
   "data": {
      "id": "1",
      "status": "active",
      "statusDetails": "confirmed",
      "email": "[email protected]",
      "customFields": {
         "referenceId": "edd-124",
         "source": "woocommerce"
      },
      "tags": [],
      "series": [],
      "timestamp": 1702513540,
      "eventUuid": "f5543f6b-f445-4343-1a17-b44db65add21"
   }
}
json
{
   "data": {
      "id": "1",
      "status": "active",
      "statusDetails": "confirmed",
      "email": "[email protected]",
      "customFields": {
         "fullName": "test"
      },
      "tags": [
         "tagName1",
         "tagName2"
      ],
      "series": [
         {
            "id": "01hsft8kccmm3hmy4nrevxtmft",
            "name": "Welcome Series"
         }
      ],
      "timestamp": 1702513540
   }
}
json
{
   "message": "The email field is required when id is not present. (and 2 more errors)",
   "errors": {
      "email": [
         "The email field is required when id is not present."
      ],
      "source": [
         "The source field is required."
      ],
      "id": [
         "The id field is required when email is not present."
      ]
   },
   "status_code": 422
}

Delete person

DELETE api/people/{idOrEmail}

Permanently remove a person by their ID or email address

URL Parameters

Request

bash
curl --request DELETE \
    "https://api.lindris.com/api/people/[email protected]" \
    --header "Authorization: Bearer {YOUR_API_KEY}" \
    --header "Content-Type: application/json"
php
$client = new \GuzzleHttp\Client();
$url = 'https://api.lindris.com/api/people/[email protected]';
$response = $client->delete(
    $url,
    [
        'headers' => [
            'Authorization' => 'Bearer {YOUR_API_KEY}',
            'Content-Type' => 'application/json',
        ],
    ]
);
$body = $response->getBody();
print_r(json_decode((string) $body));
javascript
const url = new URL(
    "https://api.lindris.com/api/people/[email protected]"
);

const headers = {
    "Authorization": "Bearer {YOUR_API_KEY}",
    "Content-Type": "application/json",
    "Accept": "application/json",
};

fetch(url, {
    method: "DELETE",
    headers,
}).then(response => response.json());

Responses

text
(No response body)
json
{
   "message": "Person not found"
}