# Titanium.Contacts

The top-level Contacts module, used for accessing and modifying the system contacts address book.

Availability
0.8
0.8
9.2.0
4.1.0

# Overview

See examples for more information.

# iOS Platform Notes

On iOS, the contacts database may be modified by an external application, causing any Person or Group objects you've retrieved to be out of sync with the database. The IDs of these objects are not guaranteed to remain the same, so updating an object when it is out of sync may have unpredictable results.

To avoid this, listen for the Titanium.Contacts.reload event. When you receive a reload event, you should assume that any existing Person or Group objects are invalid and reload them from the Contacts module before modifying them.

See the examples for a sample use of the reload event.

If 'ABAddressBookErrorDomain error 0' occurs, it implies that you are not allowed to add or edit certain fields. Check your default account in the iOS settings under contacts. If it's not 'iCloud', most likely it will not support fields such as alternateBirthday or socialProfile.

These APIs are unavailable on macOS if the app is built on a version of Xcode < 12.

# Examples

# Request access to the address book

var performAddressBookFunction = function(){...};
var addressBookDisallowed = function(){...};
if (Ti.Contacts.hasContactsPermissions()) {
    performAddressBookFunction();
} else {
    Ti.Contacts.requestContactsPermissions(function(e) {
        if (e.success) {
            performAddressBookFunction();
        } else {
            addressBookDisallowed();
        }
    });
}

# Query Existing System Address Book Records

Output to the console all properties of all people.

var singleValue = [
  'recordId', 'firstName', 'middleName', 'lastName', 'fullName', 'prefix', 'suffix', 
  'nickname', 'firstPhonetic', 'middlePhonetic', 'lastPhonetic', 'organization', 
  'jobTitle', 'department', 'note', 'birthday', 'created', 'modified', 'kind'
];
var multiValue = [
  'email', 'address', 'phone', 'instantMessage', 'relatedNames', 'date', 'url'
];
var people = Ti.Contacts.getAllPeople();
Ti.API.info('Total contacts: ' + people.length);
for (var i=0, ilen=people.length; i<ilen; i++){
  Ti.API.info('---------------------');
  var person = people[i];
  for (var j=0, jlen=singleValue.length; j<jlen; j++){
    Ti.API.info(singleValue[j] + ': ' + person[singleValue[j]]);
  }
  for (var j=0, jlen=multiValue.length; j<jlen; j++){
    Ti.API.info(multiValue[j] + ': ' + JSON.stringify(person[multiValue[j]]));
  }
}

# Add New System Address Book Records

Create two new records in the system address book. Note that the Titanium.Contacts.Person object is queried in the same way that it is created (as shown in the previous example.)

Ti.API.info('Saving contact...');
Ti.Contacts.createPerson({
  firstName: 'Paul',
  lastName: 'Dowsett',
  address:{
    work:[
      {
        CountryCode: 'gb', // determines how the address is displayed
        Street: '200 Brook Drive\nGreen Park',
        City: 'Reading',
        County: 'Berkshire',
        Country: 'England',
        ZIP: 'RG2 6UB'
      },
      {
        CountryCode: 'gb', // determines how the address is displayed
        Street: '1 St Pauls Road\nClerkenwell',
        City: 'City of London',
        State: 'London',
        Country: 'England',
        ZIP: 'EC1 1AA'
      }
    ],
    home:[
      {
        CountryCode: 'gb', // determines how the address is displayed
        Street: '2 Boleyn Court',
        City: 'London',
        State: 'Greenwich',
        Country: 'England',
        ZIP: 'SE10'
      }
    ]
  },
  birthday: '2012-01-01T12:00:00.000+0000',
  instantMessage:{
    home:[
      {
        service: 'AIM',
        username: 'leisureAIM'
      },
      {
        service: 'MSN',
        username: 'no_paul_here@msn.com'
      }
    ],
    work:[
      {
        service: 'AIM',
        username: 'seriousAIM'
      }
    ]
  },
  organization: 'Appcelerator',
  phone:{
    mobile: ['07900 000001', '07900 000002'],
    work: ['+44 (0)118 925 6128', '+44 (0)118 000 0000']
  },
  url:{
    homepage: ['www.google.com'],
    work: ['www.appcelerator.com', 'www.example.com']
  }
});
Ti.API.info('Contact saved');

Ti.API.info('Saving contact...');
var workAddress1 = {
  'CountryCode': 'us',
  'Street':  '440 N. Bernardo Avenue',
  'City': 'Mountain View',
  'State': 'California',
  'Country': 'United States',
  'ZIP': '94043'
};

Ti.Contacts.createPerson({
  firstName:'Arthur',
  lastName:'Evans',
  address:{
    'work':[workAddress1]
  }
});
Ti.API.info('Contact saved');

# Repopulate contact data if it was modified externally

Listen for the reload event to repopulate the contact data if it was modified externally, for example, in the iOS Contacts app.

var win = Ti.UI.createWindow();
var table = Ti.UI.createTableView();

// Repopulate contact data
function reloadContacts() {
    var contacts = Ti.Contacts.getAllPeople();
    var data = [];
    for (var i = 0; i < contacts.length; i++) {
        var title = contacts[i].fullName;
        if (!title || title.length === 0) {
            title = "(no name)";
        }
        var row = Ti.UI.createTableViewRow({
            title: title
        });
        data.push(row);
    }
    table.data = data;
}

Ti.Contacts.addEventListener('reload', function(e){
    alert('Reloading contacts. Your contacts were changed externally!');
    reloadContacts();
});

// initial call to populate contact data
reloadContacts();

win.add(table);
win.open();

# Properties

# contactsAuthorization READONLY

Availability
2.1.3
2.1.3
9.2.0
4.1.0
contactsAuthorization :Number

Returns an authorization constant indicating if the application has access to the address book.

Always returns AUTHORIZATION_AUTHORIZED on iOS pre-6.0 and Android devices.

If contactsAuthorization is AUTHORIZATION_RESTRICTED, you should not attempt to re-authorize: this will lead to issues.


# includeNote

Availability
8.2.1
9.2.0
includeNote :Boolean

A boolean value that indicates whether to fetch the notes stored in contacts or not.

This property need to be set before calling contacts APIs. From iOS 13 or later if your app fetch note field from contact, the app must have to set key 'com.apple.developer.contacts.notes' to 'true' in entitelements section of tiapp.xml.

<key>com.apple.developer.contacts.notes</key>
<true/>

See more details at https://developer.apple.com/documentation/bundleresources/entitlements/com_apple_developer_contacts_notes and https://developer.apple.com/contact/request/contact-note-field.

Default: true

# Methods

# createGroup

Availability
0.8
0.8
9.2.0
4.1.0
createGroup([parameters]) Titanium.Contacts.Group

Creates and returns an instance of Titanium.Contacts.Group.

This method must be followed by save to commit its changes.

Parameters

Name Type Description
parameters Dictionary<Titanium.Contacts.Group>

Properties to set on a new object, including any in Titanium.Contacts.Group except those marked as non-creation or read-only.

Returns


# createPerson

Availability
2.1.0
0.8
9.2.0
4.1.0
createPerson([parameters]) Titanium.Contacts.Person

Creates and returns an instance of Titanium.Contacts.Person, and commits all pending changes to the underlying contacts database.

Parameters

Name Type Description
parameters Dictionary<Titanium.Contacts.Person>

Properties to set on a new object, including any in Titanium.Contacts.Person except those marked as non-creation or read-only.

Returns


# getAllGroups

Availability
0.8
0.8
9.2.0
4.1.0
getAllGroups() Array<Titanium.Contacts.Group>

Gets all groups.

Returns


# getAllPeople

Availability
0.8
0.8
9.2.0
4.1.0
getAllPeople(limit) Array<Titanium.Contacts.Person>

Gets all people, unless a limit is specified.

Parameters

Name Type Description
limit Number

Maximum number of people. Android only.

Returns


# getGroupByID DEPRECATED

Availability
0.8
0.8
9.2.0
4.1.0
getGroupByID(id) Titanium.Contacts.Group

DEPRECATED SINCE 5.0.0

Use the getGroupByIdentifier method instead.

Gets the group with the specified identifier.

Parameters

Name Type Description
id Number

Group identifier.

Returns


# getGroupByIdentifier

Availability
0.8
5.0.0
9.2.0
4.1.0
getGroupByIdentifier(id) Titanium.Contacts.Group

Gets the group with the specified identifier.

Parameters

Name Type Description
id String

Group identifier.

Returns


# getPeopleWithName

Availability
0.8
0.8
9.2.0
4.1.0
getPeopleWithName(name) Array<Titanium.Contacts.Person>

Gets people with a firstName, middleName or lastName field, or a combination of these fields, that match the specified name.

Parameters

Name Type Description
name String

Name to match.

Returns


# getPersonByID DEPRECATED

Availability
0.8
0.8
9.2.0
4.1.0
getPersonByID(id) Titanium.Contacts.Person

DEPRECATED SINCE 5.0.0

Use the getPersonByIdentifier method instead.

Gets the person with the specified identifier.

Parameters

Name Type Description
id Number

Contact identifier.

Returns


# getPersonByIdentifier

Availability
5.0.0
5.0.0
9.2.0
5.0.0
getPersonByIdentifier(id) Titanium.Contacts.Person

Gets the person with the specified identifier.

Parameters

Name Type Description
id Number

Contact identifier.

Returns


# hasContactsPermissions

Availability
5.1.0
5.1.0
9.2.0
hasContactsPermissions() Boolean

Returns true if the app has contacts access.

Returns

Type
Boolean

# removeGroup

Availability
0.8
0.8
9.2.0
4.1.0
removeGroup(group) void

Removes a group from the address book.

This method must be followed by save to commit its changes.

Parameters

Name Type Description
group Titanium.Contacts.Group

Contact group.

Returns

Type
void

# removePerson

Availability
2.1.0
0.8
9.2.0
4.1.0
removePerson(person) void

Removes a contact from the address book.

On iOS:

This method must be followed by a save action to commit the data to the underlying database, which can be done explicitly using save or implicitly using createPerson. Although the Titanium.Contacts.Person object will still exist once committed, it will no longer be valid. Continuing to use it will result in unpredictable behavior, including crashes.

On Android:

This method will remove the person from the Contacts book automatically.

Parameters

Name Type Description
person Titanium.Contacts.Person

Contact.

Returns

Type
void

# requestAuthorization DEPRECATED

Availability
2.1.3
2.1.3
requestAuthorization(callback) void

DEPRECATED SINCE 5.1.0

Use the requestContactsPermissions method instead.

If authorization is unknown, will bring up a dialog requesting permission.

Note that the callback may be synchronous or asynchronous. That is, it may be called during requestAuthorization or much later. See the "Request access to the address book" example on how to best use this method.

Parameters

Name Type Description
callback Callback<ContactsAuthorizationResponse>

Callback function to execute when when authorization is no longer unknown.

Returns

Type
void

# requestContactsPermissions

Availability
5.1.0
5.1.0
9.2.0
4.1.0
requestContactsPermissions([callback]) Promise<ContactsAuthorizationResponse>

Requests for contacts access.

On Android, the request view will show if the permission is not accepted by the user, and the user did not check the box "Never ask again" when denying the request. If the user checks the box "Never ask again," the user has to manually enable the permission in device settings.

This method requests Manifest.permission.READ_CONTACTS and Manifest.permission.WRITE_CONTACTS on Android. If you require other permissions, you can also use requestPermissions.

In iOS 6, Apple introduced the Info.plist key NSContactsUsageDescription that is used to display an own description while authorizing contacts permissions. In iOS 10, this key is mandatory and the application will crash if your app does not include the key. Check the Apple docs for more information.

Parameters

Name Type Description
callback Callback<ContactsAuthorizationResponse>

Function to call upon user decision to grant contacts access. Optional on SDK 10, as this method will return a Promise, which may be used to handle the result.

Returns

On SDK 10+, this method will return a Promise whose resolved value is equivalent to that passed to the optional callback argument.

Type
Promise<ContactsAuthorizationResponse>

# revert

Availability
0.8
0.8
9.2.0
4.1.0
revert() void

Reverts all changes made by the previous save to the address book. Deprecated for >= iOS9.

Returns

Type
void

# save

Availability
3.0.0
0.8
9.2.0
4.1.0
save(contacts) void

Commits all pending changes to the underlying contacts database.

On Android:

Takes an array of Titanium.Contacts.Person objects and saves changes for the specified contacts only.

Parameters

Name Type Description
contacts Array<Titanium.Contacts.Person>

List of contacts to save. Used on Android only.

Returns

Type
void

# showContacts

Availability
0.8
0.8
9.2.0
4.1.0
showContacts(params) void

Displays a picker that allows a person to be selected.

Parameters

Name Type Description
params showContactsParams

Argument containing parameters for this method. Optional on Android.

Returns

Type
void

# Events

# reload

Availability
3.1.0
9.2.0

Fired when the database backing the contacts module is modified externally.

If you have an existing reference to a Person or Group object, you should obtain a new reference from the Contacts module. Using the existing object may result in unpredictable behavior, such as updating the wrong contact.

# Constants

# AUTHORIZATION_AUTHORIZED

Availability
2.1.3
2.1.3
9.2.0
4.1.0
AUTHORIZATION_AUTHORIZED :Number

A contactsAuthorization value indicating that the application is authorized to use the address book.

This value is always returned on Android devices, as well as on iOS versions earlier than 6.0.


# AUTHORIZATION_DENIED

Availability
2.1.3
2.1.3
9.2.0
4.1.0
AUTHORIZATION_DENIED :Number

A contactsAuthorization value indicating that the application is not authorized to use the address book.


# AUTHORIZATION_RESTRICTED DEPRECATED

Availability
2.1.3
2.1.3
9.2.0
4.1.0
AUTHORIZATION_RESTRICTED :Number

DEPRECATED SINCE 8.0.0

iOS 9 and later does not use this constant anymore. Use the other available AUTHORIZATION_* constants instead.

A contactsAuthorization value indicating that the application is not authorized to use the address book and the user cannot change this application's status.


# AUTHORIZATION_UNKNOWN

Availability
2.1.3
2.1.3
9.2.0
4.1.0
AUTHORIZATION_UNKNOWN :Number

A contactsAuthorization value indicating that the authorization state is unknown.


# CONTACTS_KIND_ORGANIZATION

Availability
0.8
0.8
9.2.0
4.1.0
CONTACTS_KIND_ORGANIZATION :Number

Specifies that a contact is an organization.

Used with the kind property.

One of the group of contact "kind" constants CONTACTS_KIND_ORGANIZATION, and CONTACTS_KIND_PERSON.


# CONTACTS_KIND_PERSON

Availability
0.8
0.8
9.2.0
4.1.0
CONTACTS_KIND_PERSON :Number

Specifies that a contact is a person.

Used with the kind property. One of the group of contact "kind" constants CONTACTS_KIND_ORGANIZATION, and CONTACTS_KIND_PERSON.


# CONTACTS_SORT_FIRST_NAME

Availability
0.8
0.8
9.2.0
4.1.0
CONTACTS_SORT_FIRST_NAME :Number

Specifies that group members will be sorted by first name.

Used with the sortedMembers method. One of the group of contact group "sort" constants CONTACTS_SORT_FIRST_NAME, and CONTACTS_SORT_LAST_NAME.


# CONTACTS_SORT_LAST_NAME

Availability
0.8
0.8
9.2.0
4.1.0
CONTACTS_SORT_LAST_NAME :Number

Specifies that group members will be sorted by last name.

Used with the sortedMembers method. One of the group of contact group "sort" constants CONTACTS_SORT_FIRST_NAME, and CONTACTS_SORT_LAST_NAME.