Members - Heyloyalty/api GitHub Wiki

Request types

Member requests takes 5 types: GET, POST, PUT, PATCH and DELETE.

Name Description
GET will fetch a member
POST will create a member
PUT will update a member – any existing fields not defined will have its data deleted when using PUT
PATCH will update specified fields on a member and leave any unsent fields untouched
DELETE will delete a member

List members

Lists the members of a list.

GET /lists/:listid/members

Parameters

Name Description Default
page The page set to recieve 1
perpage The number of members per page. Maximum perpage is 5.000 50
orderby The name of the field to order by created_at
order The order direction. Ascending: 1, Descending: -1. 1
filter See filtering.
logic The filtering logic to apply when using multiple filters. Can be "and" or "or". and

Filtering

Members can be filtered using a number of different conditional operators. For example, to get members who's first name is John, the eq operator can be used on the firstname field.

filter[firstname][eq][]=john

To find members who's first name is either John or Jane:

logic=or&filter[firstname][eq][]=john&filter[firstname][eq][]=jane

Notice that the logic parameter is set to "or". This means that only one of the given filter conditions must be met for at member to be matched.

The following conditional operators are available:

Name Description Applies to
eq Equal to text, number, date, boolean, single choice
neq Not equal to text, number, date, boolean, single choice
sw Starts with text
ew Ends with text
ct Contains text
nct Does not contain text
gt Greater than number, date
gte Greater than or equal to number, date
lt Less than number, date
lte Less than or equal to number, date
in In single choice, multiple choice
nin Not in single choice, multiple choice
ina In all multiple choice
ie Is empty text, number, date, boolean, single choice, multiple choice
nie Not is empty text, number, date, boolean, single choice, multiple choice

When filtering a choice field, the id of the targetet options(s) should be used.

Filters are case insensitive.

Response

Status: 200 OK

{
    "page": 1,
    "per_page": 50,
    "total": 2020,
    "members": [
        {
            "id": "a0d02a94-33b1-4879-bc6f-9c7388181b2d",
            "status": {
                "status": "active",
                "email": null,
                "mobile": null
            },
            "opt_in": null,
            "opt_in_date": null,
            "sent_mail": 0,
            "sent_sms": 0,
            "sent_push": null,
            "open_count": 0,
            "open_count_push": null,
            "open_rate": 0,
            "click_count": 0,
            "click_rate": 0,
            "imported": false,
            "created_at": "2020-07-27 13:09:08",
            "updated_at": "2020-07-27 13:17:10",
            "created_by": "",
            "deleted_from": null,
            "inSegment": true,
            "birthdate": "1992-08-22 00:00:00",
            "lastname": "Doe",
            "sex": {
                "value": "Kvinde",
                "id": 2
            },
            "firstname": "Jane",
            "email": "[email protected]",
            "interests": [
                {
                    "value": "Music",
                    "id": 1
                },
                {
                    "value": "Books",
                    "id": 2
                },
                {
                    "value": "Sports",
                    "id": 6
                },
                {
                    "value": "Cooking",
                    "id": 6
                },
                {
                    "value": "Art & Design",
                    "id": 9
                }
            ],
            "country": {
                "value": "Danmark",
                "id": 53
            }
        },
        ...
    ]
}

Define member status

If you wish to only see results for members with a specific status (active, unsubscribed or temporary) you can define this as a parameter. The parameter i "show" followed by the status. This parameter can be combined with regular filtering.

the following status' are available:

Name Value returns
show active only active members (default if not set)
show removed only unsubscribed members
show temporary only temporary members (These are removed after 30 days of temporary status)

The "show" parameter is optional. If "Show" is not set as a parameter, we will default to returning active members.

GET /lists/:listid/members?show=removed


No members
Status 200 ok

{"page": 1,"per_page": 50,"total": 0,"members": [] }

Error response

List not found
Status 404 list not found

Get a single member

Gets member details by a given id.

GET /lists/:listid/members/:id

Parameters

The method takes no parameters.

Response

Status: 200 OK

{
"id": "a0d02a94-33b1-4879-bc6f-9c7388181b2d",
"status": {
    "status": "active",
    "email": null,
    "mobile": null
},
"opt_in": null,
"opt_in_date": null,
"created_from": {
    "type": "api"
},
"updated_from": [],
"open_rate": 0,
"click_rate": 0,
"fields": {
    "firstname": {
        "required_in_shop": null,
        "visible_in_shop": 1,
        "order": null,
        "lock": "",
        "fallback": null,
        "type": "fixed",
        "format": "text",
        "name": "firstname",
        "label": "First Name",
        "value": "Jane"
    },
    "lastname": {
        "required_in_shop": null,
        "visible_in_shop": 1,
        "order": null,
        "lock": "",
        "fallback": null,
        "type": "fixed",
        "format": "text",
        "name": "lastname",
        "label": "Last Name",
        "value": "Doe"
    },
    "email": {
        "required_in_shop": null,
        "visible_in_shop": 1,
        "order": null,
        "lock": "",
        "fallback": null,
        "type": "fixed",
        "format": "text",
        "name": "email",
        "label": "E-mail",
        "value": "[email protected]"
    },
    "sex": {
        "required_in_shop": null,
        "visible_in_shop": 1,
        "order": null,
        "lock": "",
        "fallback": null,
        "type": "fixed",
        "format": "choice",
        "name": "sex",
        "label": "Sex",
        "options": {
            "1": "Male",
            "2": "Female"
        },
        "value": 2
    },
    "interests": {
        "required_in_shop": null,
        "visible_in_shop": 1,
        "order": 0,
        "lock": "",
        "fallback": null,
        "type": "custom",
        "format": "multi",
        "name": "interests",
        "label": "interests",
        "options": {
            "1": "Music",
            "2": "Books",
            "3": "Movies",
            "4": "Gaming",
            "5": "Travel",
            "6": "Sports",
            "7": "Cooking",
            "8": "Shopping",
            "9": "Art & Design"
        },
        "value": [
            1,
            2,
            6,
            7,
            9
        ]
    }
},
"system_fields": [],
"created_at": "2020-07-27 13:09:08",
"updated_at": "2020-07-27 13:09:08",
"unsubscribed_at": "2020-07-27 13:09:08",
"deleted_from": null,
"reference_from": null,
"moved_at": null,
"moved_from": null,
"vouchers": null
}

Error response

List not found
Status 404 list not found

Member not found
Status 404 member not found

Create a member

Adds a new member to the list specified by an id.
NB: If you plan on using gender or country, please check out these notes: https://support.heyloyalty.com/hc/en-us/articles/115001593169-3-8-API

POST /lists/:listid/members

Parameters

You can get the members parameters by calling the list first GET /lists/:id

Each field value for the member is passed as postfields. For example, if the list has a firstname, lastname and email field, the postfields should be:

firstname=John&lastname=Doe&[email protected]

A value for every field is not required, however, a value for either the email or mobile field must be provided.

For fields of type Single choice or Multiple choice, the value must be an id of the field option. Multiple options must be passed as an array.

[email protected]&interests[]=1&interests[]=2

Values for date fields must be provided in the format yyyy-mm-dd.

Response

Returns the id of the newly created member.

Status: 201 Created

{"id":"51a70b7cedf2886b17000000"}

NB: if your list has mail opt-in active (default setting on any new list), you will recieve the "201 Created" status, even though the member is pending opt-in. The member will not appear normally on the list in Heyloyalty, but you can search for it, using the search function.

Error response

List not found
Status 404 list not found

Missing field
Status 400 bad request

{"error":  "Either email or mobile field must be filled"}}

NB: Make sure to allow the API to respond, when creating members, otherwise you may accidentally create the same member, before the API can return on events.

NB: If you use opt-in on your list and wish to skip the opt-in automation and create the member as an active member instead of a temporary member, you can use the parameter "skipOptIn" with the value "1". Sending a member, with this parameter will set the member as active and skip the temporary status and the automation set in place for opting in.

Edit a member

Updates an existing member. You can use either PUT or PATCH

PUT

PUT /lists/:listid/members/:id

Parameters

The same parameters as Create member applies.

Note that this method overrides all field values for the given member. This means you can't update a sigle fields value, and leave the rest of the values as is.

PATCH

PATCH /lists/:listid/members/:id

Parameters

The same parameters as Create member applies.

Note this method allows you to update one or several fields on a member, without affecting the others. Any fields not sent along in the PATCH CALL will not be updated. This is useful, if you want to minimize the amount of data sent, when updating a member.

NOTE: If you have been using our smartupdate and it’s set to ON, you can continue using PUT as an update on existing lists, that only updates a single field and leaves the rest of them untouched.

Response

Status: 204 No Content

The method does not return anything on success.

Error response

List not found
Status 404 list not found

Member not found
Status 404 not found

Missing field
Status 400 bad request

{"error":  "Either email or mobile field must be filled"}}

Delete a member

Deletes a member.

DELETE /lists/:listid/members/:id

Parameters

The method takes no parameters.

Response

Status: 204 No Content

The method does not return anything on success.

Error response

List not found not found
Status 404 list not found

Member not found
Status 404 not found

Delete multiple instances of a member

Deletes a member on one or more lists. Note this function uses the v2 endpoint

DELETE loyalty/v2/lists/members/byfield

To delete members using this function, you need to add a raw json body.

Example

{
	"field": "email",
	"value": "[email protected],
	"lists": [1]
}
  • "field" can be either "email" og "mobile"
  • "value" is what you wish to search for and delete.
  • "lists" is an optional array. If defined in the respons, you need to define each lists you wish to delete the member from. If "lists" is not defined (not send in your request) we will look at every list on your account.

Response

Status: 200

Responsbody:

[
	{
		"list_id": 1,
		"member_id": "12345678-1234-1234-1234-123456787654",
	}
]

Note

Make sure, not to update unsubscribed members. This will change the information originally given by the subscriber. This is not adviced. If the subscriber wishes to resubscribe, you should create a new member.

Anonymize or obscure member

If you wish to anonymize a members data (right to be forgotten), you can use the DELETE route on a member (incl. memberID) and add "/obscure" to the route.

DELETE/loyalty/v1/lists/{id}/members/{memberId}/obscure

This will obscure all memberdata (this i irreversible). Only members who have been unsubscribed, can be obscured.

Import members

Import adds or updates members in bulk

POST /lists/:listid/import

Parameters

Name Description Default
fields_selected Array of fields that import file contains, should correspond to list fields Needs at least mobile or email
date_format Date format for all dates included in import file. Dateformat should be d-m-Y, example 21-10-1995 d-m-Y
skip_header_line Whether or not the import file has a header line, meaning to skip the first line in import file 1 or 0
trigger_autoresponder Should autoresponders be triggered when importing members 1 or 0
trigger_optin Should the opt-in automation be triggered when importing members 1 or 0
handle_existing How to update imported members, if member already exists in list (decided by "duplicate_field"). Options are: update (create new member or update if member exists), updateOnly (does not create new member, only updates existing) or ignore (ignores existing members only creates new) update, updateOnly or ignore
empty_field Should existing data be deleted if not included in importfile. Default is 0 set to keep data, where selected is empty 1 or 0
duplicate_field Which list field is recognized as duplicate Can be any list field, normally email or mobile
sendErrorsTo Which email to send import errors to Any valid email
delimiter Which character is used to separate columns komma, semicolon, pipe or colon

Import file format is default CSV format, and can contain header or not.

Example

Here we use standard list fields, and custom list fields, points and date_last_payment, example:

firstname,lastname,email,mobile,points,date_last_payment
john,doe,[email protected],12345678,227,2015-01-01
jane,doe,[email protected],87654321,880,2015-01-02

All parameters are sent as POST fields:

Name Example
fields_selected [firstname,lastname,mobile,points,date_last_payment]
date_format d-m-Y
skip_header_line 1
trigger_autoresponder 1
trigger_optin 1
handle_existing update
duplicate_field email
sendErrorsTo [email protected]
delimiter , ;

Full POST for fields would look like this:

fields_selected[]=firstname&fields_selected[]=lastname&fields_selected[]=email&fields_selected[]=mobile&fields_selected[]=points&fields_selected[]=date_last_payment&date_format=Y-m-d&skip_header_line=1&trigger_autoresponder=1&trigger_optin=1&handle_existing=update&duplicate_field=email&[email protected]

Now the last thing is to add POST file as text/csv

NOTE: If you want your automations to trigger but skip the opt-in from certain imports, you need to define "trigger_autoresponder" as 1 and "trigger_optin" as 0. This will create the new members without asking them to opt-in.

Response

Statuscode 200 OK

Error response

Statuscode 500 "Internal Server Error"

Statuscude 400 "The selected field {fieldname} does not exist on the list {listname}"

Other import errors will be sent to sendErrorsTo parameter

Daily import limit

Accounts have a maximum of available imports for any given day. If you exceed your limit, the api will let you know, you've hit your limit. The limit depends on your account licens.

Countrycodes

For more info, use our overview of the API bulk setup here

Move member between lists on account

This will move a member from one list to another.

POST v1/lists/:listid/members/bulk/[action]

Action is a variable to define if member should be moved from one list to another or copied from one list to another. replace [action] with either copy or move

Name Example
move moves the member from one list to specified list (see parameters). This will NOT trigger opt-in or send out welcome-emails.
copy copy will create a new member on specified list (see parameters). a New member will trigger opt-in and welcome-emails

Parameters

Name explanation options
listId takes the recipient list ID, the members should be moved or created on :listid (int)
handleDuplicates[field] Defines which field(s) should be use as unique identifier in case member exists on recipient list email, mobile, both
handleDuplicates[action] defines what action should be taken, when moving/copying members. Patch with new data, otherwise keep existing. Update with new data and delete the rest. Skip duplicates-check and create new member (duplicates can occur). patch, update, skip
members[0] defines which member is moved/copied. You can add more members, by adding multiple members[], eg: members[1] :memberId

NOTE

If a member exists on the recipient list and you're updating/patching members, this member will be updated. This means the existing members (on the recipient list) memberId will be kept and the member you moved/copied will be removed.

Example

/v1/lists/:listid/members/bulk/copy?listId=1&handleDuplicates[field]=email&handleDuplicates[action]=patch&members[0]=111111-2222-3333-4444-5555555555

Example with multiple members

/v1/lists/:listid/members/bulk/copy?listId=1&handleDuplicates[field]=email&handleDuplicates[action]=patch&members[0]=111111-2222-3333-4444-5555555555&members[1]=aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeee

Response status

Status: 200 OK

Reponse Body

{ "count": true }

⚠️ **GitHub.com Fallback** ⚠️