Contacts API v2

Google Contacts API v2 Developer's Guide - Protocol

Important: Versions 1 and 2 of the Google Contacts API have been officially deprecated as of April 20, 2012. They will continue to work as per our deprecation policy, but we encourage you to move to version 3.

The Contacts Data API allows client applications to view and update a user's contacts. Contacts are stored in the user's Google Account; most Google services have access to the contact list.

Your client application can use the Contacts Data API to create new contacts, edit or delete existing contacts, and query for contacts that match particular criteria.

In addition to providing some background on the capabilities of the Contacts Data API, this document provides examples of how to interact with contacts using XML and HTTP. After reading this document, you may wish to learn more about interacting with the API using our client libraries by reading the programming-language-specific sections of this developer's guide.

Contents

Audience

This document is intended for programmers who want to write client applications that can interact with Google's contact lists using HTTP and XML.

This document assumes that you understand the general ideas behind the Google Data APIs protocol.

If you're using a UNIX system and you want to try the examples in this document without writing any code, you may find the UNIX command-line utilities curl or wget useful; for more information, see the manual pages for those utilities.

For Contacts Data API reference information, see the Protocol reference guide.

Getting started

Creating a Google Account

You may want to sign up for a Google Account for testing purposes. Contacts are associated with Google Accounts, so if you already have a Google Account, you're all set.

Note: To view your contacts without using the Contacts Data API, you can log in to Gmail and click the Contacts link.

Authenticating

All Contacts Data API feeds are private. Thus, your client needs to authenticate before accessing a contacts feed. It can authenticate using either of two approaches: ClientLogin username/password authentication or AuthSub proxy authentication.

For more information about authentication with Google Data APIs in general, see the authentication documentation.

AuthSub proxy authentication

AuthSub proxy authentication is used by web applications that need to authenticate their users to Google Accounts. The website operator and the client code don't have access to the username and password for the user; instead, the client obtains special AuthSub tokens that allow the client to act on a particular user's behalf. For more detailed information, see the AuthSub documentation.

When a user first visits your application, they have not yet been authenticated. In this case, you need to display some information and a link directing the user to a Google page to authenticate your request for access to their contacts.

The following query parameters are included in the AuthSubRequest URL:

Parameter Description
next The URL of the page that Google should redirect the user to after authentication.
scope Indicates that the application is requesting a token to access contacts feeds. The scope string to use is http://www.google.com/m8/feeds/ (URL-encoded, of course).
secure Indicates whether the client is requesting a secure token.
session Indicates whether the token returned can be exchanged for a multi-use (session) token.

If you aren't requesting a secure token, the AuthSubRequest URL might look like this:

https://www.google.com/accounts/AuthSubRequest?scope=http%3A%2F%2Fwww.google.com%2Fm8%2Ffeeds%2F&session=1&secure=0&next=http%3A%2F%2Fwww.example.com%2Fwelcome.html

The user follows the link to Google's site and authenticates to their Google Account.

After the user authenticates, the AuthSub system redirects them to the URL you specified in the next query parameter of the AuthSubRequest URL. The AuthSub system appends an authentication token to that URL, as the value of the token query parameter. For example:

http://www.example.com/welcome.html?token=yourAuthToken

This token value represents a single-use AuthSub token. In this example, since session=1 was specified, this token can be exchanged for an AuthSub session token by calling the AuthSubSessionToken service with the single-use token in an Authorization header like this:

GET /accounts/AuthSubSessionToken HTTP/1.1
Content-Type: application/x-www-form-urlencoded
Authorization: AuthSub token="yourAuthToken"
User-Agent: Java/1.5.0_06
Host: www.google.com
Accept: text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2
Connection: keep-alive

The AuthSubSessionToken service response includes a Token header that contains the session token and an Expiration header that indicates how long the token will remain valid.

Your application can then use the session token value in the Authorization header of subsequent interactions with contacts.

Here's an example of an HTTP request, containing a non-secure token, that you might send to request a contacts feed:

GET /m8/feeds/contacts/liz%40gmail.com/full HTTP/1.1
Content-Type: application/x-www-form-urlencoded
Authorization: AuthSub token="yourSessionToken"
User-Agent: Java/1.5.0_06
Host: www.google.com
Accept: text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2
Connection: keep-alive

ClientLogin username/password authentication

Use ClientLogin authentication if your client is a standalone, single-user "installed" client (such as a desktop application). To request an authentication token using the ClientLogin mechanism, send a POST request to the following URL:

https://www.google.com/accounts/ClientLogin

The POST body should contain a set of query parameters that look like parameters passed by an HTML form, using the application/x-www-form-urlencoded content type. These parameters are:

Parameter Description
accountType Type of account to be authenticated. The default is GOOGLE; if you want to support Google Apps users, use HOSTED_OR_GOOGLE.
Email The user's email address.
Passwd The user's password.
service The service name for contacts feeds is cp. (For other service names, see the service name list.)
source Identifies your client application. Should take the form companyName-applicationName-versionID. The examples use the name exampleCo-exampleApp-1.

For more information about the parameters, see the Authentication for Installed Applications document.

If the authentication request fails, then the server returns an HTTP 403 Forbidden status code.

If it succeeds, then the server returns an HTTP 200 OK status code, plus three long alphanumeric codes in the body of the response: SID, LSID, and Auth. The Auth value is the authorization token that you'll send with each of your subsequent contacts-feed requests, so keep a copy of that value. You can ignore the SID and LSID values.

Since all requests to private feeds require authentication, you have to set the Authorization header in all subsequent interactions with contacts feeds, using the following format:

Authorization: GoogleLogin auth=yourAuthToken

Where yourAuthToken is the Auth string returned by the ClientLogin request.

For more information about ClientLogin authentication, including sample requests and responses, see the Account Authentication for Installed Applications documentation.

Note: Use the same token for all requests in a given session; don't acquire a new token for each contacts request.

Contacts feed URL

The feed URL is in one of the following forms:

https://www.google.com/m8/feeds/contacts/userEmail/full
https://www.google.com/m8/feeds/contacts/default/full

Note: "full" can be replaced with other projection values You can also substitute default for the user's email address, which tells the server to return the contacts for the user whose credentials accompany the request.

Note: Only the authenticated user's email address can be specified in the URL.

Specifying a version

Every request that you send using the Contacts Data API should specify version 2 of the API.

To specify a version number, use the GData-Version HTTP header:

GData-Version: 2

Alternatively, if you can't set HTTP headers, you can specify v=2 as a query parameter in the URL. But the HTTP header is preferred where possible.

Note: The client libraries supply appropriate version headers automatically, so don't use the v=2 query parameter when you're using a client library.

Creating contacts

After authenticating, you can publish new contact entries.

First, create an XML representation of the contact to publish. This XML needs to be in the form of an Atom <entry> element, which might look like this:

<atom:entry xmlns:atom='http://www.w3.org/2005/Atom'
    xmlns:gd='http://schemas.google.com/g/2005'>
  <atom:category scheme='http://schemas.google.com/g/2005#kind'
    term='http://schemas.google.com/contact/2008#contact' />
  <atom:title type='text'>Elizabeth Bennet</atom:title>
  <atom:content type='text'>Notes</atom:content>
  <gd:email rel='http://schemas.google.com/g/2005#work'
    address='liz@gmail.com' />
  <gd:email rel='http://schemas.google.com/g/2005#home'
    address='liz@example.org' />
  <gd:phoneNumber rel='http://schemas.google.com/g/2005#work'
    primary='true'>
    (206)555-1212
  </gd:phoneNumber>
  <gd:phoneNumber rel='http://schemas.google.com/g/2005#home'>
    (206)555-1213
  </gd:phoneNumber>
  <gd:im address='liz@gmail.com'
    protocol='http://schemas.google.com/g/2005#GOOGLE_TALK'
    rel='http://schemas.google.com/g/2005#home' />
  <gd:postalAddress rel='http://schemas.google.com/g/2005#work'
    primary='true'>
    1600 Amphitheatre Pkwy Mountain View
  </gd:postalAddress>
</atom:entry>

To publish this entry, send it to the contact-list post URL as follows. First, place your Atom <entry> element in the body of a new POST request, using the application/atom+xml content type. Then send it to the post URL. For example, to add a contact to the contact list belonging to liz@gmail.com, post the new entry to the following URL:

https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full

The Google server creates a contact using the entry you sent, then returns an HTTP 201 CREATED status code, along with a copy of the new contact in the form of an <entry> element. The entry returned is the same one you sent, but it also contains various elements added by the server, such as an <id> element.

Note: A contact's photo cannot be set while creating a contact. See: Photo management.

If your request fails for some reason, Google may return a different status code. For information about the status codes, see the Google Data API protocol reference document.

Retrieving contacts

Retrieving all contacts

To retrieve the user's contacts, send an HTTP GET request to the contacts feed URL. Google then returns a feed containing the appropriate contact entries. For example, to get a list of contacts for liz@gmail.com, send the following HTTP request:

GET https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full

The feed then returns an HTTP 200 OK status code and a standard Atom 1.0 feed containing the contacts.

Note: The feed may not contain all of the user's contacts, because there's a default limit on the number of results returned. For more information, see the max-results query parameter in Retrieving contacts using query parameters.

The following is an example of a contacts feed with only one entry.

<feed xmlns='http://www.w3.org/2005/Atom'
    xmlns:openSearch='http://a9.com/-/spec/opensearch/1.1/'
    xmlns:gContact='http://schemas.google.com/contact/2008'
    xmlns:batch='http://schemas.google.com/gdata/batch'
    xmlns:gd='http://schemas.google.com/g/2005'
    gd:etag='W/"CUMBRHo_fip7ImA9WxRbGU0."'>
  <id>liz@gmail.com</id>
  <updated>2008-12-10T10:04:15.446Z</updated>
  <category scheme='http://schemas.google.com/g/2005#kind'
    term='http://schemas.google.com/contact/2008#contact' />
  <title>Elizabeth Bennet's Contacts</title>
  <link rel='http://schemas.google.com/g/2005#feed'
    type='application/atom+xml'
    href='https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full' />
  <link rel='http://schemas.google.com/g/2005#post'
    type='application/atom+xml'
    href='https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full' />
  <link rel='http://schemas.google.com/g/2005#batch'
    type='application/atom+xml'
    href='https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full/batch' />
  <link rel='self' type='application/atom+xml'
    href='https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full?max-results=25' />
  <author>
    <name>Elizabeth Bennet</name>
    <email>liz@gmail.com</email>
  </author>
  <generator version='1.0' uri='http://www.google.com/m8/feeds'>
    Contacts
  </generator>
  <openSearch:totalResults>1</openSearch:totalResults>
  <openSearch:startIndex>1</openSearch:startIndex>
  <openSearch:itemsPerPage>25</openSearch:itemsPerPage>
  <entry gd:etag='"Qn04eTVSLyp7ImA9WxRbGEUORAQ."'>
    <id>
      http://www.google.com/m8/feeds/contacts/liz%40gmail.com/base/c9012de
    </id>
    <updated>2008-12-10T04:45:03.331Z</updated>
    <app:edited xmlns:app='http://www.w3.org/2007/app'>2008-12-10T04:45:03.331Z</app:edited>
    <category scheme='http://schemas.google.com/g/2005#kind'
      term='http://schemas.google.com/contact/2008#contact' />
    <title>Fitzwilliam</title>
    <link rel='http://schemas.google.com/contacts/2008/rel#photo' type='image/*'
      href='https://www.google.com/m8/feeds/photos/media/liz%40gmail.com/c9012de'
      gd:etag='"KTlcZWs1bCp7ImBBPV43VUV4LXEZCXERZAc."' />
    <link rel='self' type='application/atom+xml'
      href='https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full/c9012de' />
    <link rel='edit' type='application/atom+xml'
      href='https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full/c9012de' />
    <gd:phoneNumber rel='http://schemas.google.com/g/2005#home'
      primary='true'>
      456
    </gd:phoneNumber>
    <gd:extendedProperty name='pet' value='hamster' />
    <gContact:groupMembershipInfo deleted='false'
      href='http://www.google.com/m8/feeds/groups/liz%40gmail.com/base/270f' />
  </entry>
</feed>

Retrieving contacts using query parameters

The Contacts Data API lets you request a set of contacts that match specified criteria, such as requesting contacts updated after a given date.

For example, to send a date-range query, add the updated-min parameter to the request URL. To get all the contact entries updated after March 16, 2007, send an HTTP request to the contact's feed URL:

GET https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full?updated-min=2007-03-16T00:00:00

When you send that GET request, the server returns an HTTP 200 OK status code and a feed containing any contacts that were created or updated after the date specified.

The Contacts Data API supports query parameters described in the Contacts Data API Reference Guide (see also: Google Data APIs Reference Guide). In particular, there is no support for full-text queries or locating a contact by email address.

Hint: To track incremental changes to a contact list, do the following: When you send a request for a feed, keep track of the value of the feed's <updated> element. Then you can later retrieve only the contacts that have changed since the previous request by setting the query parameter updated-min to that <updated> value, and setting showdeleted to true.

Note: By default, the entries in a feed are not ordered.

Retrieving a single contact

To retrieve a specific contact, send an HTTP GET request to the contact's self link. The server returns a contact entry. For example, to get a contact with self link set to https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full/12345, send the following HTTP request:

GET https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full/12345

The server then returns an HTTP 200 OK status code and an entry containing the contact.

Note: Retrieving a single contact requires prior knowledge of the entry's self link, which can only be obtained by locating the corresponding entry in the contacts feed. See Retrieving all contacts and Retrieving contacts using query parameters for more information.

Retrieving a contact again

If you want to retrieve a contact that you've retrieved before, you can improve efficiency by telling the server to send the contact only if it has changed since the last time you retrieved it.

To do this sort of conditional retrieval, send an HTTP GET request that includes an HTTP If-None-Match header. In the header, specify the contact's ETag, which you can find in the <entry> element's gd:etag attribute.

For example:

If-None-Match: "Qn04eTVSLyp7ImA9WxRbGEUORAQ."

When the server receives this request, it checks to see whether the contact that you requested has the same ETag as the ETag you specified. If the ETags match, then the contact hasn't changed, and the server returns an HTTP 304 Not Modified status code.

If the ETags don't match, then the contact has been modified since the last time you requested it, and the server returns the contact.

For more information about ETags, see the Google Data APIs reference guide.

Retrieving a photo for a contact

To retrieve a photo for a contact, send an HTTP GET request to the photo link of this contact. The server returns bytes of the photo. For example, to get the latest version of a photo for a contact with an element:

<link rel='http://schemas.google.com/contacts/2008/rel#photo' type='image/*'
    href='http://google.com/m8/feeds/photos/media/liz%40gmail.com/c9012de'
    gd:etag='"KTlcZWs1bCp7ImBBPV43VUV4LXEZCXERZAc."'/>

send the following HTTP request:

GET http://google.com/m8/feeds/photos/media/liz%40gmail.com/c9012de

The server then returns an HTTP 200 OK status code and the photo.

Note: If a contact does not have a photo, then the photo link element has no gd:etag attribute.

Note: When using photo links, an authorization token in the HTTP header has to be specified. For more details please take a look at: Authenticating.

Updating contacts

To update an existing contact, first retrieve the entry you want to update, modify it, and then send a PUT request with the updated entry in the message body to the contact's edit URL. Use the application/atom+xml content type.

To make sure that your update doesn't overwrite another client's changes, include an HTTP If-Match header that contains the original contact's ETag value. You can determine the original contact's ETag value by examining the <entry> element's gd:etag attribute.

If you want to update the contact regardless of whether someone else has updated it since you retrieved it, then use If-Match: * and don't include the ETag.

For more information about ETags, see the Google Data APIs reference guide.

Note: The contact's name is stored in the <atom:title> element.

Be sure that the <id> value in the entry you PUT exactly matches the <id> of the existing entry. The edit URL is highlighted in the following entry:

<entry gd:etag='"Q3k4cTVSLyp7ImA9WxRXFkwJRAA."'>
  <id>http://www.google.com/m8/feeds/contacts/liz%40gmail.com/base/8411573</id>
  <updated>2008-02-28T18:47:02.303Z</updated>
  <category scheme='http://schemas.google.com/g/2005#kind'
    term='http://schemas.google.com/contact/2008#contact' />
  <title>Jo</title>
  <content type='text'>Notes</content>
  <link rel='http://schemas.google.com/contacts/2008/rel#photo' type='image/*'
    href='https://www.google.com/m8/feeds/photos/media/liz%40gmail.com/8411573' />
  <link rel='self' type='application/atom+xml'
    href='https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full/8411573' />
  <link rel='edit' type='application/atom+xml'
    href='https://www.google.com/m8/feeds/contacts/liz%40gmail.com/full/8411573' />
  <gd:phoneNumber rel='http://schemas.google.com/g/2005#other'
    primary='true'>456-123-2133</gd:phoneNumber>
  <gd:extendedProperty name='pet' value='hamster' />
  <gd:extendedProperty name='cousine'>
    <italian />
  </gd:extendedProperty>
  <gContact:groupMembershipInfo deleted='false'
    href='http://www.google.com/m8/feeds/groups/liz%40gmail.com/base/270f' />
</entry>

Important: To ensure forward compatibility, be sure that when you PUT an updated entry you preserve all the XML that was present when you retrieved the entry from the server. Otherwise the ignored elements will be deleted. The Google Data API client libraries all handle this correctly, so if you're using one of the libraries you're all set.

Troubleshooting Tip: Some firewalls block HTTP PUT messages. To get around this, you can include a X-HTTP-Method-Override: PUT header in a POST request. For details, see the Google Data API protocol basics document.

Important: Setting extended properties (gd:extendedElement elements) is allowed only within full or property-NAME projection.

Contact photo management

Every contact has a photo link element. It has the form:

<link rel='http://schemas.google.com/contacts/2008/rel#photo' type='image/*'
  href='https://www.google.com/m8/feeds/photos/media/liz%40gmail.com/c9012de'
  gd:etag='"KTlcZWs1bCp7ImBBPV43VUV4LXEZCXERZAc."'>

That element appears whether the contact has an associated photo or not. If the contact does have a photo, then the element contains a gd:etag attribute specifying an ETag for the photo. If the contact has no photo, then there's no gd:etag attribute, and the href attribute provides the URL to use to add a photo to the contact.

To add or update a photo given the <link> element shown above, send a new photo with a PUT command to the URL: https://www.google.com/m8/feeds/photos/media/liz%40gmail.com/c9012de. Remember to set a proper "image/*" Content-Type header.

To delete a photo, send an HTTP DELETE request to the same URL.

When updating or deleting a photo, send the photo's ETag in the If-Match header of the HTTP request. Alternatively, use If-Match: * to update or delete regardless of whether you have the latest version of the photo.

For more information about ETags, see the Google Data APIs reference guide.

Note: When using photo links, authorization token in HTTP header has to be specified. For more details please take a look at: Authenticating.

Deleting contacts

To delete a contact, send a DELETE request to the contact's edit URL. This is the same URL used to update contacts. (Google retains placeholders for deleted contacts for 30 days after deletion; during that time, you can request the placeholders using the showdeleted query parameter.)

If you want to make sure that you don't delete a contact that has been changed by another client since you retrieved it, include an HTTP If-Match header that contains the original contact's ETag value. You can determine the original contact's ETag value by examining the <entry> element's gd:etag attribute.

If you want to delete the contact regardless of whether someone else has updated it since you retrieved it, then use If-Match: * and don't include the ETag. (In this case, you don't need to retrieve the contact before deleting it.)

For more information about ETags, see the Google Data APIs reference guide.

Troubleshooting Tip: Some firewalls block HTTP DELETE messages. To get around this, you can include a X-HTTP-Method-Override: DELETE header in a POST request. For details, see the Google Data API protocol basics document.

Note: To update existing contacts, see Updating contacts; don't update by deleting contacts and then re-adding them.

Managing contact groups

Contacts can be placed into user-defined groups. You can create, retrieve, update, and delete these groups using the Contacts Data API, and you can add contacts to a group or remove contacts from a group. For details, see the following sections.

The Contacts Data API also provides access to four predefined "system groups" for each user:

  • My Contacts
  • Friends
  • Family
  • Coworkers

System groups appear in a groups feed just like user-defined groups do. In fact, system groups are mostly treated just like other groups. The differences are:

  • Each system group entry contains a <gContact:systemGroup> subelement. The id attribute of that subelement indicates which system group the group is: Contacts, Friends, Family, or Coworkers. Note that the My Contacts ID value is simply Contacts, without the "My". Also note that this system group ID value is different from the group ID given in the group entry's <id> element.
  • You can't add new system groups, change the name of a system group, add extended properties to a system group, or delete a system group.
  • The contact-group entry representing a system group doesn't contain a rel="edit" link.

Note: System groups' names are not guaranteed to be localized, so in general your client is responsible for presenting the system groups in a way appropriate for your users, such as by providing localized names for the system groups, or representing them using icons.

Contact groups feed URL

The feed URL is in one of the following forms:

https://www.google.com/m8/feeds/groups/userEmail/full
https://www.google.com/m8/feeds/groups/default/full

Note: "full" can be replaced with other projection values. You can also substitute default for the user's email address, which tells the server to return the contact groups for the user whose credentials accompany the request.

Note: Only the authenticated user's email address can be specified in the URL.

Operations on contact groups are analogous to those for contacts.

Changing group membership

To determine what groups a given contact belongs to, examine the contact's <gContact:groupMembershipInfo> elements. Each such element contains a group ID as the value of its href attribute.

To add a contact to a group, your client needs to know the group ID, which can be found as the value of the <id> element for that group in a groups feed.

Note: This is true even for system groups. Note that the <id> element value is different from the "system group ID" that appears in the <gContact:systemGroup> element for system groups. To determine the My Contacts group's ID, for example, you can retrieve a feed of all the groups for a given user, then find the group entry that has the <gContact:systemGroup id="Contacts"> subelement, and take the value of that group entry's <id> element.

After you have the group's ID, update the contact to add a new <gContact:groupMembershipInfo> element that specifies that group ID.

To remove a contact from a group, update the contact to remove the appropriate <gContact:groupMembershipInfo> element.

All of these group-membership operations work the same way for system groups as for user-defined groups.

Creating contact groups

You can publish new contact groups entries after authenticating.

Example of a group entry:

<atom:entry xmlns:gd="http://schemas.google.com/g/2005">
  <atom:category scheme="http://schemas.google.com/g/2005#kind"
    term="http://schemas.google.com/contact/2008#group"/>
  <atom:title type="text">Salsa group</atom:title>
  <gd:extendedProperty name="more info about the group">
    <info>Nice people.</info>
  </gd:extendedProperty>
</atom:entry>

To publish this entry, send it to the contact-list post URL as follows. First, place your Atom <entry> element in the body of a new POST request, using the application/atom+xml content type. Then send it to the post URL. For example, to add a contact group to the contact groups list belonging to jo@gmail.com, post the new entry to the following URL (contact groups feed URL):

https://www.google.com/m8/feeds/groups/jo%40gmail.com/full

The Google server creates a contact group using the entry you sent, then returns an HTTP 201 CREATED status code, along with a copy of the new contact group in the form of an <entry> element. The entry returned is the same one you sent, but it also contains various elements added by the server, such as an <id> element.

Retrieving contact groups

Retrieving all contact groups

To retrieve the user's contact groups, send an HTTP GET request to the contact groups feed URL. Google then returns a feed containing the appropriate contact entries. For example, to get a list of contact groups for jo@gmail.com, send the following HTTP request:

GET https://www.google.com/m8/feeds/groups/jo%40gmail.com/full

The feed then returns an HTTP 200 OK status code and a standard Atom 1.0 feed containing the contact groups.

An example of a contact group feed containing the system groups and one user-defined group (with most of the system groups left out for ease of readability):

<feed xmlns='http://www.w3.org/2005/Atom'
    xmlns:openSearch='http://a9.com/-/spec/opensearch/1.1/'
    xmlns:gContact='http://schemas.google.com/contact/2008'
    xmlns:batch='http://schemas.google.com/gdata/batch'
    xmlns:gd='http://schemas.google.com/g/2005'
    gd:etag='W/"D08MQnc-fSp7ImA9WxRbGU0."'>
  <id>jo@gmail.com</id>
  <updated>2008-12-10T10:44:43.955Z</updated>
  <category scheme='http://schemas.google.com/g/2005#kind'
    term='http://schemas.google.com/contact/2008#group' />
  <title>Jo March's Contact Groups</title>
  <link rel='alternate' type='text/html'
    href='http://www.google.com/' />
  <link rel='http://schemas.google.com/g/2005#feed'
    type='application/atom+xml'
    href='https://www.google.com/m8/feeds/groups/jo%40gmail.com/thin' />
  <link rel='http://schemas.google.com/g/2005#post'
    type='application/atom+xml'
    href='https://www.google.com/m8/feeds/groups/jo%40gmail.com/thin' />
  <link rel='http://schemas.google.com/g/2005#batch'
    type='application/atom+xml'
    href='https://www.google.com/m8/feeds/groups/jo%40gmail.com/thin/batch' />
  <link rel='self'
    type='application/atom+xml'
    href='https://www.google.com/m8/feeds/groups/jo%40gmail.com/thin?max-results=25' />
  <author>
    <name>Jo March</name>
    <email>jo@gmail.com</email>
  </author>
  <generator version='1.0'
    uri='http://www.google.com/m8/feeds'>Contacts</generator>
  <openSearch:totalResults>5</openSearch:totalResults>
  <openSearch:startIndex>1</openSearch:startIndex>
  <openSearch:itemsPerPage>25</openSearch:itemsPerPage>
  <entry gd:etag='"YDwqeyI."'>
    <id>http://www.google.com/m8/feeds/groups/jo%40gmail.com/base/6</id>
    <updated>1970-01-01T00:00:00.000Z</updated>
    <category scheme='http://schemas.google.com/g/2005#kind'
      term='http://schemas.google.com/contact/2008#group' />
    <title>System Group: My Contacts</title>
    <content>System Group: My Contacts</content>
    <link rel='self' type='application/atom+xml'
      href='https://www.google.com/m8/feeds/groups/jo%40gmail.com/thin/6' />
    <gContact:systemGroup id='Contacts' />
  </entry>
  [[]...Other system groups removed for ease of reading...]
  <entry gd:etag='"Rn05fDVSLyp7ImA9WxRbGEUORQM."'>
    <id>http://www.google.com/m8/feeds/groups/jo%40gmail.com/base/68f415478ba1aa69</id>
    <updated>2008-12-10T04:44:37.324Z</updated>
    <category scheme='http://schemas.google.com/g/2005#kind'
      term='http://schemas.google.com/contact/2008#group' />
    <title>joggers</title>
    <content>joggers</content>
    <link rel='self' type='application/atom+xml'
      href='https://www.google.com/m8/feeds/groups/jo%40gmail.com/thin/68f415478ba1aa69' />
    <link rel='edit' type='application/atom+xml'
      href='https://www.google.com/m8/feeds/groups/jo%40gmail.com/thin/68f415478ba1aa69' />
  </entry>
</feed>

Retrieving contact groups using query parameters

The Contacts Data API supports query parameters described in the Contacts Data API Reference Guide (see also: Google Data APIs Reference Guide).

It allows a user to request a set of contact groups that match specified criteria, such as requesting contact groups updated after a given date.

For example, to send a date-range query, add the updated-min parameter to the request URL. To get all the contact-group entries updated after March 16, 2007, send an HTTP request to the contact group's feed URL:

GET https://www.google.com/m8/feeds/groups/jo%40gmail.com/full?updated-min=2007-03-16T00:00:00

When you send that GET request, the server returns an HTTP 200 OK status code and a feed containing any contact groups that were created or updated after the date specified.

Note: By default, the entries in a feed are not ordered.

Retrieving a single group for a contact

To retrieve a single group entry for a group that a given contact belongs to, send an HTTP GET request to the link from gContact:groupMembershipInfo element from the contact's entry.

For example, for a contact with

<gContact:groupMembershipInfo deleted="false" href="http://google.com/m8/feeds/groups/jo%40gmail.com/base/68f415478ba1aa69"/> 

element, send the following HTTP request:

GET https://www.google.com/m8/feeds/groups/jo%40gmail.com/base/68f415478ba1aa69

The server then returns an HTTP 200 OK status code and an entry containing the contact group.

Note: The feed may not contain all of the user's contact groups, because there's a default limit on the number of results returned. For more information, see the max-results query parameter in Retrieving contact groups using query parameters.

Updating contact groups

This section describes how to update a contact group's name or extended properties. To change a group member's membership, see Changing group membership.

To update an existing contact group's name or properties, first you retrieve the entry you want to update. Then you modify it, and then you send a PUT request, with the updated entry in the message body, to the contact's edit URL. Use the application/atom+xml content type. Be sure that the <id> value in the entry you PUT exactly matches the <id> of the existing entry.

Feed entry example with edit URL highlighted:

<entry xmlns:gd="http://schemas.google.com/g/2005"
    gd:etag="&quot;Rno4ezVSLyp7ImA9WxdTEUgNRQU.&quot;">
  <category scheme="http://schemas.google.com/g/2005#kind"
    term="http://schemas.google.com/g/2005#group"/>
  <id>http://www.google.com/feeds/groups/jo%40gmail.com/base/1234</id>
  <published>2005-01-18T21:00:00Z</published>
  <updated>2006-01-01T00:00:00Z</updated>
  <title type="text">Salsa group</title>
  <content type="text">Salsa group</content>
  <link rel='self' type='application/atom+xml'
    href= 'https://www.google.com/m8/feeds/groups/jo%40gmail.com/full/2' />
  <link rel='edit' type='application/atom+xml'
    href='https://www.google.com/m8/feeds/groups/jo%40gmail.com/full/2'/>
  <gd:extendedProperty name="more info about the group">
    <info>Very nice people.</info>
  </gd:extendedProperty>
</entry>

After a successful update the server returns an HTTP 200 OK together with the updated entry.

Important: To ensure forward compatibility, be sure that when you PUT an updated entry you preserve all the XML that was present when you retrieved the entry from the server. Otherwise the ignored elements will be deleted. The Google Data API client libraries all handle this correctly, so if you're using one of the libraries you're all set.

Deleting contact groups

To delete a contact group, send a DELETE request to the contact group's edit URL. This is the same URL used to update contact groups. (Google retains placeholders for deleted contact groups for 30 days after deletion; during that time, you can request the placeholders using the showdeleted query parameter.) HTTP's code 200 OK means the successful operation.

Troubleshooting Tip: Some firewalls block HTTP DELETE messages. To get around this, you can include a X-HTTP-Method-Override: DELETE header in a POST request. For details, see the Google Data API protocol basics document.

Note: To update existing contact groups, see Updating contact groups; don't update by deleting contact groups and then re-adding them.

Batch operations

If you're performing a lot of operations, the time it takes to send and and receive all those HTTP messages can really add up, making your app slow and unresponsive. With batch requests you can have the server perform multiple operations with a single HTTP request. The basic idea is that you create a contacts or contact groups feed and add an entry for each operation you want to perform.

The following snippet shows a batch request that contains two create operations, however you can use also querying, updating, and deleting contacts or contact groups. Most of the unnecessary elements have been omitted.

<?xml version='1.0' encoding='UTF-8'?>
<feed xmlns='http://www.w3.org/2005/Atom'
      xmlns:gContact='http://schemas.google.com/contact/2008'
      xmlns:gd='http://schemas.google.com/g/2005'
      xmlns:batch='http://schemas.google.com/gdata/batch'>
  <category scheme='http://schemas.google.com/g/2005#kind' term='http://schemas.google.com/g/2008#contact' />
  <entry>
    <batch:id>1</batch:id>
    <batch:operation type='insert' />
    <category scheme='http://schemas.google.com/g/2005#kind' term='http://schemas.google.com/g/2008#contact'/>
    <title type='text'>Contact 1</title>
    <gd:email rel='http://schemas.google.com/g/2005#home' address='contact1@gmail.com' primary='true'/>
  </entry>
  <entry>
    <batch:id>2</batch:id>
    <batch:operation type='insert' />
    <category scheme='http://schemas.google.com/g/2005#kind' term='http://schemas.google.com/g/2008#contact'/>
    <title type='text'>Contact 2</title>
    <gd:email rel='http://schemas.google.com/g/2005#home' address='contact2@gmail.com' primary='true'/>
  </entry>
</feed>

Batch requests are limited to 100 operations at a time. You can find more information about batch operations in the Google Data APIs Batch Processing documentation.

Note: The update and delete entries require gd:etag attributes, to avoid overwriting another client's changes.

Back to top

Authentication required

You need to be signed in with Google+ to do that.

Signing you in...

Google Developers needs your permission to do that.