Monday, January 21, 2013

Android - print all contacts properties


In this article I will show you, how you can print out all the contacts from an Android device.

If you are trying to work with contacts on Android, you have probably learned, that the contacts structure is not any simple there. As a matter of fact it is not any difficult, anyway it may be challenging to figure out, how to work with all the database stuff properly, especially on older versions (<11) of the Android's API.

In short: Contacts are stored in three tables - Contacts, RawContacts and Data. Every Contacts row can be linked in several RawContacts rows and every RawContacts row can be linked in several Data rows. The links are made with ID's. Easy - isn't it?

I encourage you to read the http://developer.android.com/guide/topics/providers/contacts-provider.html document.

Following snippet shows how to print contacts information on the standard output:
 /**
   * Method wich reads user ID's from Contacts table and calls printRaw for all
   * of them
   */
  private void contacts() {
    // ID is only thing, that we are interested in
    String[] projection = new String[] { ContactsContract.Contacts._ID };
    // Get all user IDs
    Cursor cursor = getContentResolver().query(
        ContactsContract.Contacts.CONTENT_URI, projection, null, null, null);
    if (cursor.moveToFirst()) {
      while (!cursor.isAfterLast()) {
        System.out.println("######################");
        printRaw(cursor.getString(cursor
            .getColumnIndex(ContactsContract.Contacts._ID)));
        cursor.moveToNext();
      }
    }
  }
  
  /**
   * For given user ID finds all rows in RawContacts. Then calls printData for
   * all of them
   * 
   * @param _id
   */
  private void printRaw(String _id) {
    //What we are interested in
    String[] projection = new String[] { ContactsContract.RawContacts._ID,
        ContactsContract.RawContacts.ACCOUNT_TYPE,
        ContactsContract.RawContacts.ACCOUNT_NAME };
    Cursor cursor = getContentResolver().query(
        ContactsContract.RawContacts.CONTENT_URI, projection,
        ContactsContract.RawContacts.CONTACT_ID + " = ?", new String[] { _id },
        null);
    if (cursor.moveToFirst()) {
      while (!cursor.isAfterLast()) {
        System.out.println("======="
            + cursor.getString(cursor
                .getColumnIndex(ContactsContract.RawContacts.ACCOUNT_NAME))
            + "@"
            + cursor.getString(cursor
                .getColumnIndex(ContactsContract.RawContacts.ACCOUNT_TYPE))
            + "=========");
        printData(cursor.getString(cursor
            .getColumnIndex(ContactsContract.RawContacts._ID)));
        cursor.moveToNext();
      }
    }
  }
  /**
   * This one prints all available data for the given RawContact
   * @param _id
   */
  private void printData(String _id) {
    String[] projection = new String[] { ContactsContract.Data.MIMETYPE,
        ContactsContract.Data.DATA1, ContactsContract.Data.DATA2,
        ContactsContract.Data.DATA5, ContactsContract.Data.DATA14,
        ContactsContract.Data.DATA15 };
    Cursor cursor = getContentResolver().query(
        ContactsContract.Data.CONTENT_URI, projection,
        ContactsContract.Data.RAW_CONTACT_ID + " = ?", new String[] { _id },
        null);
    if (cursor.moveToFirst()) {
      while (!cursor.isAfterLast()) {
        String mime = cursor.getString(cursor
            .getColumnIndex(ContactsContract.Data.MIMETYPE));
        if (mime.equals(StructuredName.CONTENT_ITEM_TYPE)) {
          System.out.println("Name: "
              + cursor.getString(cursor
                  .getColumnIndex(StructuredName.DISPLAY_NAME)));
        } else if (mime.equals(Phone.CONTENT_ITEM_TYPE)) {
          System.out.println("Phone: "
              + cursor.getString(cursor.getColumnIndex(Phone.NUMBER)));
        } else if (mime.equals(Email.CONTENT_ITEM_TYPE)) {
          System.out.println("E-mail: "
              + cursor.getString(cursor.getColumnIndex(Email.ADDRESS)));
        } else if (mime.equals(Photo.CONTENT_ITEM_TYPE)) {
          byte[] photo = cursor.getBlob(cursor.getColumnIndex(Photo.PHOTO));
          if (photo != null) {
            System.out.println("Photo: " + photo.length);
          }
        } else if (mime.equals(Organization.CONTENT_ITEM_TYPE)) {
          System.out.println("Organization: "
              + cursor.getString(cursor.getColumnIndex(Organization.COMPANY)));
        } else if (mime.equals(Im.CONTENT_ITEM_TYPE)) {
          System.out.println("Instant messaging: "
              + cursor.getString(cursor.getColumnIndex(Im.PROTOCOL)));
        } else if (mime.equals(Nickname.CONTENT_ITEM_TYPE)) {
          System.out.println("Nick: "
              + cursor.getString(cursor.getColumnIndex(Nickname.NAME)));
        } else if (mime.equals(Note.CONTENT_ITEM_TYPE)) {
          System.out.println("Note: "
              + cursor.getString(cursor.getColumnIndex(Note.NOTE)));
        } else if (mime.equals(StructuredPostal.CONTENT_ITEM_TYPE)) {
          System.out.println("Postal: "
              + cursor.getString(cursor
                  .getColumnIndex(StructuredPostal.FORMATTED_ADDRESS)));
        } else if (mime.equals(GroupMembership.CONTENT_ITEM_TYPE)) {
          System.out.println("Group: "
              + cursor.getString(cursor
                  .getColumnIndex(GroupMembership.GROUP_ROW_ID)));
        } else if (mime.equals(Website.CONTENT_ITEM_TYPE)) {
          System.out.println("Web: "
              + cursor.getString(cursor.getColumnIndex(Website.URL)));
        } else if (mime.equals(Event.CONTENT_ITEM_TYPE)) {
          System.out.println("Event: "
              + cursor.getString(cursor.getColumnIndex(Event.START_DATE))
              + ": " + cursor.getString(cursor.getColumnIndex(Event.TYPE)));
        } else if (mime.equals(Relation.CONTENT_ITEM_TYPE)) {
          System.out.println("Relation: "
              + cursor.getString(cursor.getColumnIndex(Relation.NAME)));
        } else if (mime.equals(SipAddress.CONTENT_ITEM_TYPE)) {
          System.out
              .println("SIP: "
                  + cursor.getString(cursor
                      .getColumnIndex(SipAddress.SIP_ADDRESS)));
        }
        cursor.moveToNext();
      }
    }
  }
Note, that just showed approach follows the contacts structure stupidly and therefore is pretty slow, due to plenty of subsequent database calls. Some more efficient way should be used in a real application - for example list records from the Data table which contains ID's of RawContact same as of the Contact directly in a one shot.

Hope this will help you.

No comments:

Post a Comment