How to import and update large numbers of contacts using bulk activity endpoints

You can import new contacts from another source into a Constant Contact account by making a POST call using either a CSV payload (/activities/contacts_file_import ) or a JSON payload (/activities/contacts_json_import).

Contacts must have either an email address or an SMS number defined. These endpoints use the email addresses or SMS number you provide in the import to determine if each contact is new or not. Importing an existing contact only updates the contact properties you include in the import request.

You can also use these endpoints to update existing contacts when syncing local data with Constant Contact. For more information on syncing contact data, see the Guidelines for Importing Contacts.

Import Limitations

The following limitations apply to the import methods:

  • File size: The size of the imported CSV file or JSON payload must be less than 4 megabytes (MB).
  • Number of contacts: The total number of rows in the CSV import file cannot exceed 40,000 (39,999 contact rows plus a headings row). The total number of contacts in the JSON payload cannot exceed 40,000.
When importing a CSV file, contacts in rows above 40,000 are not processed.
If the file size exceeds 4 MB, only the contacts contained in the first 4 MB (and in lines ≤40k) are processed.

About Permissions to Send

Permission to send signifies the type of relationship an account owner has with a contact. It is important for compliance with US and international anti-spam law. See Constant Contact’s Email Permission Policy for complete information.

Important:

  • If specifying an email address - Only use this method when a contact gives you their explicit permission to send them an email. It is a violation of anti-spam and telemarketing laws, as well as a serious violation of the Constant Contact Terms of Service to use the Opt-in features of the API to opt a contact back in without his or her own action and consent.
  • If specifying an SMS number - Only use this method when a contact gives you their explicit permission to send them an SMS. It is a violation of anti-spam and telemarketing laws, as well as a serious violation of the Constant Contact Terms of Service to use the Opt-in features of the API to opt a contact back in without his or her own action and consent.

When importing contacts:

  • permission_to_send applies to the email address and is set to Implicit by default for all new contacts created in an import activity.
  • permission_to_send is not changed for any existing contacts included in an import activity.
Constant Contact allows customers to import lists of contacts into their account. However, there are rules to be aware of when it comes to what types of email addresses they'll be able to send campaigns to.

General Guidelines for Importing Contacts

The following lists the general steps/guidelines used to import new contacts from a local source into Constant Contact.

  1. Collect the contacts to import from the local source then format the data to match the requirements of the activity import endpoint you plan to use.
  2. Import the contacts by making a POST call to the appropriate Constant Contact bulk activity import endpoint (CVS or JSON as described in the sections that follow).
  3. Check the activity status to check when the job completes. Learn more. After the import activity completes, all contacts are imported into Constant Contact and any errors are noted in the activity status.

It’s important to keep the local source in sync with the Constant Contact data. Check out How to Sync Contacts and Lists for more information.

Import Contacts from a CSV file

Make a POST call to the /activities/contacts_file_import multipart/form-data endpoint to import contacts into Constant Contact using a CSV file. This method requires a multipart/form-data request body that requires including the file and list_ids properties.

The content-type MUST be unspecified when using this endpoint.

Parameters

  • file - The CSV file containing contact data to import.
  • list_ids - The contact lists you want to add all imported contacts to as an array of contact list_id values. You must include at least one list_id value and cannot include more than 50 list_id values.
  • sms_permission_to_send - Use to set SMS permissions at the file level for all contacts with SMS numbers.
    • Set to explicit to specify that all contacts provided explicit permission. If explicit, you must also include the sms_consent_date as a column header to specify the date the contact consented to receiving SMS messages.
    • Set to not_set to specify that contacts have not yet provided consent. Though you can add an SMS number to a contact before they grant SMS permission, you must obtain explicit permission from the contact in order to send SMS messages.

CSV File Content

The import file must be in comma-separated value (CSV) format. Create the CSV file adding contact properties to the CSV header and your contact data as rows in the CSV. You can also include custom fields in the CSV file. The CSV file must contain either an email or sms_number header. This method identifies each unique contact using their email address or SMS number.

You can use the following contact properties in the CSV file:

Header Column Name Column Attributes Description
first_name optional, Max. Length:50 The first name of the contact.
last_name optional, Max. Length:50 The last name of the contact.
job_title optional, Max. Length:50 The job title of the contact.
company_name optional, Max. Length:50 The name of the company where the contact works.
anniversary optional The anniversary date for the contact. For example, this value could be the date when the contact first became a customer of an organization in Constant Contact. Valid date formats are MM/DD/YYYY, M/D/YYYY, YYYY/MM/DD, YYYY/M/D, YYYY-MM-DD, YYYY-M-D,M-D-YYYY, or M-DD-YYYY. The year must be greater than 1900 and cannot be more than 10 years in the future (with respect to the current year).
birthday_month optional, minimum 1, maximum 12 The month value for the contact’s birthday. Valid values are from 1 through 12. You must use this column with birthday_day.
birthday_day optional, minimum 1, maximum 31 The day value for the contact’s birthday. Valid values are from 1 through 31. You must use this column with birthday_month.
phone optional, Max. Length:50 The phone number for the contact.
street optional, Max. Length:255 Line one of the street address for the contact.
street2 optional, Max. Length:255 Line two of the street address for the contact. This value is automatically appended to the street value.
city optional, Max. Length:50 The name of the city where the contact lives.
state optional, Max. Length:50 The name of the state or province where the contact lives.
zip optional, Max. Length:50 A zip or postal code for the contact.
country optional, Max. Length:50 The name of the country where the contact lives.
sms_number optional The contact’s SMS phone number.
sms_consent_date string, required if sms_permission_to_send is set to explicit, Max. Length:16 The date that the contact consented to receiving SMS messages. Valid date formats are MM/DD/YYYY, M/D/YYYY, YYYY/MM/DD, YYYY/M/D, YYYY-MM-DD, YYYY-M-D,M-D-YYYY, or M-DD-YYYY.
cf:custom_field_name optional, Max. Length:255 This header column name is the name of an existing custom field prefixed with cf:. For example, enter cf:first_name if you have a custom field named “first_name”. As long as you use the cf: prefix, you can import custom fields that use the same name as the contact properties. You can add up to 25 different custom field headings for each contact.

CSV File Example

Click here to download an example CSV file.

In order to import custom field data, the custom fields must already exist in the Constant Contact account you are using. The example file uses custom fields named "first_name" and "vehicle_make_and_model_year".

Import Contacts Using JSON

Make a POST call to the /activities/contacts_json_import endpoint to import contacts using a JSON request payload. Use this method to create an asynchronous background job that adds new contacts or updates existing contacts by importing a JSON payload. Importing an existing contact only updates the contact properties you include in the request.

The request body includes:

  • import_data - Required. The contacts you are importing as an array of objects containing contact data. You must specify an email address and/or an sms_number for each contact you want to import. If including a contact’s sms_number, if the contact provided explicit permission to receive SMS messages, you must set the sms_permission_to_send property to explicit and specify the date of consent (sms_consent_date). If explicit permission was not provided, you must set sms_permission_to_send to not_set (the sms_consent_date is not required).

  • list_ids - Required. The contact lists you want to add all imported contacts to as an array of contact list_id strings. You must include at least one list_id value and cannot include more than 50 list_id values.

  • sms_permission_to_send: If a sms_number is included the request, specify if the contact gave explict SMS permission or if the SMS permission was not set (not_set). If set to explicit, the sms_consent_date is also required.

Contact Import Data Format

You can use the following contact properties with each object in the import_data array:

Property Name Property Attributes Description
email string, Max. Length:50 The email address of the contact. This method identifies each unique contact using their email address. Required if sms_number is not specified.
first_name string, optional, Max. Length:50 The first name of the contact.
last_name string, optional, Max. Length:50 The last name of the contact.
job_title string, optional, Max. Length:50 The job title of the contact.
company_name string, optional, Max. Length:50 The name of the company where the contact works.
anniversary string, optional, The anniversary date for the contact. For example, this value could be the date when the contact first became a customer of an organization in Constant Contact. Valid date formats are MM/DD/YYYY, M/D/YYYY, YYYY/MM/DD, YYYY/M/D, YYYY-MM-DD, YYYY-M-D,M-D-YYYY, or M-DD-YYYY. The year must be greater than 1900 and cannot be more than 10 years in the future (with respect to the current year).
birthday_month integer, minimum 1, maximum 12, optional The month value for the contact’s birthday. Valid values are from 1 through 12. You must use this property with birthday_day.
birthday_day integer, minimum 1, maximum 31, optional The day value for the contact’s birthday. Valid values are from 1 through 31. You must use this property with birthday_month.
phone string, required, Max. Length:50 The primary phone number for the contact. Default type = home
home_phone string, optional, Max. Length:50 The home phone number for the contact. Type = home
work_phone string, optional, Max. Length:50 The work phone number for the contact. Type = work
other_phone string, optional, Max. Length:50 Another phone number for the contact. Type = other
street string, optional, Max. Length:255 Line one of the street address for the contact. Default, type = home
street2 string, optional, Max. Length:255 Line two of the street address for the contact. This value is automatically appended to the street value. Default, type = home
other_street string, optional, Max. Length:255 Line one of the another street address for the contact. Type = other
other_street2 string, optional, Max. Length:255 Line two of the other street address for the contact. This value is automatically appended to the other_street value. Type = other
home_street string, optional, Max. Length:255 Line one of the home street address for the contact. Type = home
home_street2 string, optional, Max. Length:255 Line two of the street address for the contact. This value is automatically appended to the home_street value. Default type = home
work_street string, optional, Max. Length:255 Line one of the work street address for the contact. Type = work
work_street2 string, optional, Max. Length:255 Line two of the street address for the contact. This value is automatically appended to the work_street value. Type = work
city string, optional, Max. Length:50 The primary city name for the contact. Default, type home
home_city string, optional, Max. Length:50 The name of the city where the contact lives. Type = home
work_city string, optional, Max. Length:50 The name of the city where the contact works. Type = work
other_city string, optional, Max. Length:50 The name of another city where the contact is located. Type = other
state string, optional, Max. Length:50 The primary name of the state or province for the contact. Default type = home
other_state string, optional, Max. Length:50 Another name of a state or province for the contact. Type = other
home_state string, optional, Max. Length:50 The name of the home state or province where the contact lives. Type = home
work_state string, optional, Max. Length:50 The name of another state or province where the contact works. Type = work
zip string, optional, Max. Length:50 The primary zip or postal code for the contact. Default, type = home
home_zip string, optional, Max. Length:50 A zip or postal code for where the contact’s home is located. Type = home
work_zip string, optional, Max. Length:50 A zip or postal code for where the contact’s works. Type = work
other_zip string, optional, Max. Length:50 A zip or postal code for another location where the contact is located. Type = other
country string, optional, Max. Length:50 The name of the country where the contact lives. Default, type = home
home_country string, optional, Max. Length:50 The name of the country where the contact lives. Type = home
work_country string, optional, Max. Length:50 The name of the country where the contact works. Type = work
other_country string, optional, Max. Length:50 Another name of the country where the contact is located. Type = other
cf:custom_field_name string, optional, Max. Length:255 A contact custom field. The name of this property is dynamic based on the custom fields that you want to import. Use a key-value pair where the key is an existing custom field name prefixed with cf:, and the value is a custom field string value. As long as you use the cf: prefix, you can import custom fields that use the same name as the contact properties. You can import up to 25 custom fields in each contact.
sms_number string, Max. Length:16 The US phone number to associate with the contact’s SMS-enabled phone. Valid formats are 1231231234 or 123-123-1234. Requires a valid country code. Required if email_address is not specified.
sms_consent_date string, required if sms_permission_to_send is set to explicit, Max. Length:16 The date that the contact consented to receiving SMS messages. Valid date formats are MM/DD/YYYY, M/D/YYYY, YYYY/MM/DD, YYYY/M/D, YYYY-MM-DD, YYYY-M-D,M-D-YYYY, or M-DD-YYYY.

Import JSON Request Sample

POST https://api.cc.email/v3/activities/contacts_json_import

Endpoint Requirements

User privileges: contacts:write

Authorization scopes: contact_data

<?php

$curl = curl_init();

curl_setopt_array($curl, array(
  CURLOPT_URL => 'https://api.cc.email/v3/activities/contacts_json_import',
  CURLOPT_RETURNTRANSFER => true,
  CURLOPT_ENCODING => '',
  CURLOPT_MAXREDIRS => 10,
  CURLOPT_TIMEOUT => 0,
  CURLOPT_FOLLOWLOCATION => true,
  CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
  CURLOPT_CUSTOMREQUEST => 'POST',
  CURLOPT_POSTFIELDS =>'{
  "import_data": [
    {
      "email": "sms_explicit@example.com",
      "first_name": "Holly",
      "last_name": "Jones",
      "job_title": "Chief Innovation Officer",
      "company_name": "RelativeGravity, Inc.",
      "birthday_month": 11,
      "birthday_day": 24,
      "mobile_phone": "555-555-5555",
      "phone": "555-555-4444",
      "home_phone": "123-234-5435",
      "work_phone": "555-555-6666",
      "street": "123 Maple Lane",
      "street2": "Apt. 337",
      "city": "Chicago",
      "state": "Illinois",
      "zip": "60609",
      "country": "United States",
      "home_street": "123 Maple Lane",
      "home_street2": "Apt. 337",
      "home_city": "Chicago",
      "home_state": "Illinois",
      "home_country": "United States",
      "sms_number": "508-234-9876",
      "sms_consent_date": "08-01-2024"
    }
  ],
  "list_ids": [
    "02ec29a8-13c2-11ef-adba-6fa8f4277c8b"
  ],
  "sms_permission_to_send": "explicit"
}',
  CURLOPT_HTTPHEADER => array(
    'Accept: */*',
    'Content-Type: application/json',
    'Authorization: Bearer {access_token}'
  ),
));

$response = curl_exec($curl);

curl_close($curl);
echo $response;


curl --location 'https://api.cc.email/v3/activities/contacts_json_import' \
--header 'Accept: */*' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer {access_token}' \
--data-raw '{
  "import_data": [
    {
      "email": "sms_explicit@example.com",
      "first_name": "Holly",
      "last_name": "Jones",
      "job_title": "Chief Innovation Officer",
      "company_name": "RelativeGravity, Inc.",
      "birthday_month": 11,
      "birthday_day": 24,
      "mobile_phone": "555-555-5555",
      "phone": "555-555-4444",
      "home_phone": "123-234-5435",
      "work_phone": "555-555-6666",
      "street": "123 Maple Lane",
      "street2": "Apt. 337",
      "city": "Chicago",
      "state": "Illinois",
      "zip": "60609",
      "country": "United States",
      "home_street": "123 Maple Lane",
      "home_street2": "Apt. 337",
      "home_city": "Chicago",
      "home_state": "Illinois",
      "home_country": "United States",
      "sms_number": "508-234-9876",
      "sms_consent_date": "08-01-2024"
    }
  ],
"list_ids": [
"02ec29a8-13c2-11ef-adba-6fa8f4277c8b"
],
"sms_permission_to_send": "explicit"
}'
OkHttpClient client = new OkHttpClient().newBuilder()
  .build();
MediaType mediaType = MediaType.parse("application/json");
RequestBody body = RequestBody.create(mediaType, "{\n  \"import_data\": [\n    {\n      \"email\": \"sms4_explicit.langevin@example.com\",\n      \"first_name\": \"Holly\",\n      \"last_name\": \"Jones\",\n      \"job_title\": \"Chief Innovation Officer\",\n      \"company_name\": \"RelativeGravity, Inc.\",\n      \"birthday_month\": 11,\n      \"birthday_day\": 24,\n      \"mobile_phone\": \"555-555-5555\",\n      \"phone\": \"555-555-4444\",\n      \"home_phone\": \"123-234-5435\",\n      \"work_phone\": \"555-555-6666\",\n      \"street\": \"123 Maple Lane\",\n      \"street2\": \"Apt. 337\",\n      \"city\": \"Chicago\",\n      \"state\": \"Illinois\",\n      \"zip\": \"60609\",\n      \"country\": \"United States\",\n      \"home_street\": \"123 Maple Lane\",\n      \"home_street2\": \"Apt. 337\",\n      \"home_city\": \"Chicago\",\n      \"home_state\": \"Illinois\",\n      \"home_country\": \"United States\",\n      \"sms_number\": \"508-234-9876\",\n      \"sms_consent_date\": \"08-01-2024\"\n\n    }\n  ],\n  \"list_ids\": [\n    \"02ec29a8-13c2-11ef-adba-6fa8f4277c8b\"\n  ],\n  \"sms_permission_to_send\": \"explicit\"\n}");
Request request = new Request.Builder()
  .url("https://api.cc.email/v3/activities/contacts_json_import")
  .method("POST", body)
  .addHeader("Accept", "*/*")
  .addHeader("Content-Type", "application/json")
  .addHeader("Authorization", "Bearer {access_token}")
  .build();
Response response = client.newCall(request).execute();

Response

{
  "activity_id": "f7845aac-51b2-11ef-8032-fa163e6b01c1",
  "state": "initialized",
  "created_at": "2024-08-03T16:10:57Z",
  "updated_at": "2024-08-03T16:10:57Z",
  "source_file_name": "csv_from_json_2024-08-03T121056-040020240803-5386-1vmpaga.csv",
  "percent_done": 1,
  "activity_errors": [],
  "status": {},
  "_links": {
    "self": {
      "href": "/v3/activities/f9215aac-51b2-11ef-8032-fa163e6b01c1"
    }
  }  
}

Checking the Activity Status for Job Complete

After you send an import request, the V3 API returns a response body that includes an activity_id and the current status of the import activity. Send a GET request to the /activities/{activity_id} endpoint endpoint to determine when the V3 API has finished importing your contacts. You can also use the URL that the V3 API returns in the href response body property to send the request.

GET https://api.cc.email/v3/activities/{activity_id}

Endpoint Requirements

User privileges: contacts:write

Authorization scopes: contact_data

Try it!