1 /* 2 * Copyright (C) 2009 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License 15 */ 16 17 package com.android.providers.contacts; 18 19 import com.android.internal.content.SyncStateContentProviderHelper; 20 import com.android.providers.contacts.ContactLookupKey.LookupKeySegment; 21 import com.android.providers.contacts.ContactsDatabaseHelper.AggregatedPresenceColumns; 22 import com.android.providers.contacts.ContactsDatabaseHelper.AggregationExceptionColumns; 23 import com.android.providers.contacts.ContactsDatabaseHelper.Clauses; 24 import com.android.providers.contacts.ContactsDatabaseHelper.ContactsColumns; 25 import com.android.providers.contacts.ContactsDatabaseHelper.ContactsStatusUpdatesColumns; 26 import com.android.providers.contacts.ContactsDatabaseHelper.DataColumns; 27 import com.android.providers.contacts.ContactsDatabaseHelper.GroupsColumns; 28 import com.android.providers.contacts.ContactsDatabaseHelper.MimetypesColumns; 29 import com.android.providers.contacts.ContactsDatabaseHelper.NameLookupColumns; 30 import com.android.providers.contacts.ContactsDatabaseHelper.NameLookupType; 31 import com.android.providers.contacts.ContactsDatabaseHelper.PhoneColumns; 32 import com.android.providers.contacts.ContactsDatabaseHelper.PhoneLookupColumns; 33 import com.android.providers.contacts.ContactsDatabaseHelper.PresenceColumns; 34 import com.android.providers.contacts.ContactsDatabaseHelper.RawContactsColumns; 35 import com.android.providers.contacts.ContactsDatabaseHelper.SettingsColumns; 36 import com.android.providers.contacts.ContactsDatabaseHelper.StatusUpdatesColumns; 37 import com.android.providers.contacts.ContactsDatabaseHelper.Tables; 38 import com.google.android.collect.Lists; 39 import com.google.android.collect.Maps; 40 import com.google.android.collect.Sets; 41 42 import android.accounts.Account; 43 import android.accounts.AccountManager; 44 import android.accounts.OnAccountsUpdateListener; 45 import android.app.Notification; 46 import android.app.NotificationManager; 47 import android.app.PendingIntent; 48 import android.app.SearchManager; 49 import android.content.ContentProviderOperation; 50 import android.content.ContentProviderResult; 51 import android.content.ContentResolver; 52 import android.content.ContentUris; 53 import android.content.ContentValues; 54 import android.content.Context; 55 import android.content.IContentService; 56 import android.content.Intent; 57 import android.content.OperationApplicationException; 58 import android.content.SharedPreferences; 59 import android.content.SyncAdapterType; 60 import android.content.UriMatcher; 61 import android.content.res.AssetFileDescriptor; 62 import android.content.res.Configuration; 63 import android.database.CharArrayBuffer; 64 import android.database.Cursor; 65 import android.database.CursorWrapper; 66 import android.database.DatabaseUtils; 67 import android.database.MatrixCursor; 68 import android.database.MatrixCursor.RowBuilder; 69 import android.database.sqlite.SQLiteConstraintException; 70 import android.database.sqlite.SQLiteContentHelper; 71 import android.database.sqlite.SQLiteDatabase; 72 import android.database.sqlite.SQLiteQueryBuilder; 73 import android.database.sqlite.SQLiteStatement; 74 import android.net.Uri; 75 import android.os.AsyncTask; 76 import android.os.Bundle; 77 import android.os.MemoryFile; 78 import android.os.RemoteException; 79 import android.os.SystemClock; 80 import android.os.SystemProperties; 81 import android.pim.vcard.VCardComposer; 82 import android.pim.vcard.VCardConfig; 83 import android.preference.PreferenceManager; 84 import android.provider.BaseColumns; 85 import android.provider.ContactsContract; 86 import android.provider.LiveFolders; 87 import android.provider.OpenableColumns; 88 import android.provider.SyncStateContract; 89 import android.provider.ContactsContract.AggregationExceptions; 90 import android.provider.ContactsContract.ContactCounts; 91 import android.provider.ContactsContract.Contacts; 92 import android.provider.ContactsContract.Data; 93 import android.provider.ContactsContract.DisplayNameSources; 94 import android.provider.ContactsContract.FullNameStyle; 95 import android.provider.ContactsContract.Groups; 96 import android.provider.ContactsContract.Intents; 97 import android.provider.ContactsContract.PhoneLookup; 98 import android.provider.ContactsContract.PhoneticNameStyle; 99 import android.provider.ContactsContract.ProviderStatus; 100 import android.provider.ContactsContract.RawContacts; 101 import android.provider.ContactsContract.SearchSnippetColumns; 102 import android.provider.ContactsContract.Settings; 103 import android.provider.ContactsContract.StatusUpdates; 104 import android.provider.ContactsContract.CommonDataKinds.BaseTypes; 105 import android.provider.ContactsContract.CommonDataKinds.Email; 106 import android.provider.ContactsContract.CommonDataKinds.GroupMembership; 107 import android.provider.ContactsContract.CommonDataKinds.Im; 108 import android.provider.ContactsContract.CommonDataKinds.Nickname; 109 import android.provider.ContactsContract.CommonDataKinds.Organization; 110 import android.provider.ContactsContract.CommonDataKinds.Phone; 111 import android.provider.ContactsContract.CommonDataKinds.Photo; 112 import android.provider.ContactsContract.CommonDataKinds.StructuredName; 113 import android.provider.ContactsContract.CommonDataKinds.StructuredPostal; 114 import android.telephony.PhoneNumberUtils; 115 import android.text.TextUtils; 116 import android.util.Log; 117 118 import java.io.ByteArrayOutputStream; 119 import java.io.FileNotFoundException; 120 import java.io.IOException; 121 import java.io.OutputStream; 122 import java.text.SimpleDateFormat; 123 import java.util.ArrayList; 124 import java.util.Collections; 125 import java.util.Date; 126 import java.util.HashMap; 127 import java.util.HashSet; 128 import java.util.List; 129 import java.util.Locale; 130 import java.util.Map; 131 import java.util.Set; 132 import java.util.concurrent.CountDownLatch; 133 134 /** 135 * Contacts content provider. The contract between this provider and applications 136 * is defined in {@link ContactsContract}. 137 */ 138 public class ContactsProvider2 extends SQLiteContentProvider implements OnAccountsUpdateListener { 139 140 private static final String TAG = "ContactsProvider"; 141 142 private static final boolean VERBOSE_LOGGING = Log.isLoggable(TAG, Log.VERBOSE); 143 144 // TODO: carefully prevent all incoming nested queries; they can be gaping security holes 145 // TODO: check for restricted flag during insert(), update(), and delete() calls 146 147 /** Default for the maximum number of returned aggregation suggestions. */ 148 private static final int DEFAULT_MAX_SUGGESTIONS = 5; 149 150 private static final String GOOGLE_MY_CONTACTS_GROUP_TITLE = "System Group: My Contacts"; 151 /** 152 * Property key for the legacy contact import version. The need for a version 153 * as opposed to a boolean flag is that if we discover bugs in the contact import process, 154 * we can trigger re-import by incrementing the import version. 155 */ 156 private static final String PROPERTY_CONTACTS_IMPORTED = "contacts_imported_v1"; 157 private static final int PROPERTY_CONTACTS_IMPORT_VERSION = 1; 158 private static final String PREF_LOCALE = "locale"; 159 160 private static final String PROPERTY_AGGREGATION_ALGORITHM = "aggregation_v2"; 161 private static final int PROPERTY_AGGREGATION_ALGORITHM_VERSION = 2; 162 163 private static final String AGGREGATE_CONTACTS = "sync.contacts.aggregate"; 164 165 private static final UriMatcher sUriMatcher = new UriMatcher(UriMatcher.NO_MATCH); 166 167 private static final String TIMES_CONTACED_SORT_COLUMN = "times_contacted_sort"; 168 169 private static final String STREQUENT_ORDER_BY = Contacts.STARRED + " DESC, " 170 + TIMES_CONTACED_SORT_COLUMN + " DESC, " 171 + Contacts.DISPLAY_NAME + " COLLATE LOCALIZED ASC"; 172 private static final String STREQUENT_LIMIT = 173 "(SELECT COUNT(1) FROM " + Tables.CONTACTS + " WHERE " 174 + Contacts.STARRED + "=1) + 25"; 175 176 /* package */ static final String UPDATE_TIMES_CONTACTED_CONTACTS_TABLE = 177 "UPDATE " + Tables.CONTACTS + " SET " + Contacts.TIMES_CONTACTED + "=" + 178 " CASE WHEN " + Contacts.TIMES_CONTACTED + " IS NULL THEN 1 ELSE " + 179 " (" + Contacts.TIMES_CONTACTED + " + 1) END WHERE " + Contacts._ID + "=?"; 180 181 /* package */ static final String UPDATE_TIMES_CONTACTED_RAWCONTACTS_TABLE = 182 "UPDATE " + Tables.RAW_CONTACTS + " SET " + RawContacts.TIMES_CONTACTED + "=" + 183 " CASE WHEN " + RawContacts.TIMES_CONTACTED + " IS NULL THEN 1 ELSE " + 184 " (" + RawContacts.TIMES_CONTACTED + " + 1) END WHERE " + RawContacts.CONTACT_ID + "=?"; 185 186 /* package */ static final String PHONEBOOK_COLLATOR_NAME = "PHONEBOOK"; 187 188 private static final int CONTACTS = 1000; 189 private static final int CONTACTS_ID = 1001; 190 private static final int CONTACTS_LOOKUP = 1002; 191 private static final int CONTACTS_LOOKUP_ID = 1003; 192 private static final int CONTACTS_DATA = 1004; 193 private static final int CONTACTS_FILTER = 1005; 194 private static final int CONTACTS_STREQUENT = 1006; 195 private static final int CONTACTS_STREQUENT_FILTER = 1007; 196 private static final int CONTACTS_GROUP = 1008; 197 private static final int CONTACTS_PHOTO = 1009; 198 private static final int CONTACTS_AS_VCARD = 1010; 199 private static final int CONTACTS_AS_MULTI_VCARD = 1011; 200 201 private static final int RAW_CONTACTS = 2002; 202 private static final int RAW_CONTACTS_ID = 2003; 203 private static final int RAW_CONTACTS_DATA = 2004; 204 private static final int RAW_CONTACT_ENTITY_ID = 2005; 205 206 private static final int DATA = 3000; 207 private static final int DATA_ID = 3001; 208 private static final int PHONES = 3002; 209 private static final int PHONES_ID = 3003; 210 private static final int PHONES_FILTER = 3004; 211 private static final int EMAILS = 3005; 212 private static final int EMAILS_ID = 3006; 213 private static final int EMAILS_LOOKUP = 3007; 214 private static final int EMAILS_FILTER = 3008; 215 private static final int POSTALS = 3009; 216 private static final int POSTALS_ID = 3010; 217 218 private static final int PHONE_LOOKUP = 4000; 219 220 private static final int AGGREGATION_EXCEPTIONS = 6000; 221 private static final int AGGREGATION_EXCEPTION_ID = 6001; 222 223 private static final int STATUS_UPDATES = 7000; 224 private static final int STATUS_UPDATES_ID = 7001; 225 226 private static final int AGGREGATION_SUGGESTIONS = 8000; 227 228 private static final int SETTINGS = 9000; 229 230 private static final int GROUPS = 10000; 231 private static final int GROUPS_ID = 10001; 232 private static final int GROUPS_SUMMARY = 10003; 233 234 private static final int SYNCSTATE = 11000; 235 private static final int SYNCSTATE_ID = 11001; 236 237 private static final int SEARCH_SUGGESTIONS = 12001; 238 private static final int SEARCH_SHORTCUT = 12002; 239 240 private static final int LIVE_FOLDERS_CONTACTS = 14000; 241 private static final int LIVE_FOLDERS_CONTACTS_WITH_PHONES = 14001; 242 private static final int LIVE_FOLDERS_CONTACTS_FAVORITES = 14002; 243 private static final int LIVE_FOLDERS_CONTACTS_GROUP_NAME = 14003; 244 245 private static final int RAW_CONTACT_ENTITIES = 15001; 246 247 private static final int PROVIDER_STATUS = 16001; 248 249 private interface DataContactsQuery { 250 public static final String TABLE = "data " 251 + "JOIN raw_contacts ON (data.raw_contact_id = raw_contacts._id) " 252 + "JOIN contacts ON (raw_contacts.contact_id = contacts._id)"; 253 254 public static final String[] PROJECTION = new String[] { 255 RawContactsColumns.CONCRETE_ID, 256 DataColumns.CONCRETE_ID, 257 ContactsColumns.CONCRETE_ID 258 }; 259 260 public static final int RAW_CONTACT_ID = 0; 261 public static final int DATA_ID = 1; 262 public static final int CONTACT_ID = 2; 263 } 264 265 private interface DataDeleteQuery { 266 public static final String TABLE = Tables.DATA_JOIN_MIMETYPES; 267 268 public static final String[] CONCRETE_COLUMNS = new String[] { 269 DataColumns.CONCRETE_ID, 270 MimetypesColumns.MIMETYPE, 271 Data.RAW_CONTACT_ID, 272 Data.IS_PRIMARY, 273 Data.DATA1, 274 }; 275 276 public static final String[] COLUMNS = new String[] { 277 Data._ID, 278 MimetypesColumns.MIMETYPE, 279 Data.RAW_CONTACT_ID, 280 Data.IS_PRIMARY, 281 Data.DATA1, 282 }; 283 284 public static final int _ID = 0; 285 public static final int MIMETYPE = 1; 286 public static final int RAW_CONTACT_ID = 2; 287 public static final int IS_PRIMARY = 3; 288 public static final int DATA1 = 4; 289 } 290 291 private interface DataUpdateQuery { 292 String[] COLUMNS = { Data._ID, Data.RAW_CONTACT_ID, Data.MIMETYPE }; 293 294 int _ID = 0; 295 int RAW_CONTACT_ID = 1; 296 int MIMETYPE = 2; 297 } 298 299 300 private interface RawContactsQuery { 301 String TABLE = Tables.RAW_CONTACTS; 302 303 String[] COLUMNS = new String[] { 304 RawContacts.DELETED, 305 RawContacts.ACCOUNT_TYPE, 306 RawContacts.ACCOUNT_NAME, 307 }; 308 309 int DELETED = 0; 310 int ACCOUNT_TYPE = 1; 311 int ACCOUNT_NAME = 2; 312 } 313 314 public static final String DEFAULT_ACCOUNT_TYPE = "com.google"; 315 public static final String FEATURE_LEGACY_HOSTED_OR_GOOGLE = "legacy_hosted_or_google"; 316 317 /** Sql where statement for filtering on groups. */ 318 private static final String CONTACTS_IN_GROUP_SELECT = 319 Contacts._ID + " IN " 320 + "(SELECT " + RawContacts.CONTACT_ID 321 + " FROM " + Tables.RAW_CONTACTS 322 + " WHERE " + RawContactsColumns.CONCRETE_ID + " IN " 323 + "(SELECT " + DataColumns.CONCRETE_RAW_CONTACT_ID 324 + " FROM " + Tables.DATA_JOIN_MIMETYPES 325 + " WHERE " + Data.MIMETYPE + "='" + GroupMembership.CONTENT_ITEM_TYPE 326 + "' AND " + GroupMembership.GROUP_ROW_ID + "=" 327 + "(SELECT " + Tables.GROUPS + "." + Groups._ID 328 + " FROM " + Tables.GROUPS 329 + " WHERE " + Groups.TITLE + "=?)))"; 330 331 /** Sql for updating DIRTY flag on multiple raw contacts */ 332 private static final String UPDATE_RAW_CONTACT_SET_DIRTY_SQL = 333 "UPDATE " + Tables.RAW_CONTACTS + 334 " SET " + RawContacts.DIRTY + "=1" + 335 " WHERE " + RawContacts._ID + " IN ("; 336 337 /** Sql for updating VERSION on multiple raw contacts */ 338 private static final String UPDATE_RAW_CONTACT_SET_VERSION_SQL = 339 "UPDATE " + Tables.RAW_CONTACTS + 340 " SET " + RawContacts.VERSION + " = " + RawContacts.VERSION + " + 1" + 341 " WHERE " + RawContacts._ID + " IN ("; 342 343 /** Name lookup types used for contact filtering */ 344 private static final String CONTACT_LOOKUP_NAME_TYPES = 345 NameLookupType.NAME_COLLATION_KEY + "," + 346 NameLookupType.EMAIL_BASED_NICKNAME + "," + 347 NameLookupType.NICKNAME + "," + 348 NameLookupType.NAME_SHORTHAND + "," + 349 NameLookupType.ORGANIZATION + "," + 350 NameLookupType.NAME_CONSONANTS; 351 352 353 /** Contains just BaseColumns._COUNT */ 354 private static final HashMap<String, String> sCountProjectionMap; 355 /** Contains just the contacts columns */ 356 private static final HashMap<String, String> sContactsProjectionMap; 357 /** Contains just the contacts columns */ 358 private static final HashMap<String, String> sContactsProjectionWithSnippetMap; 359 360 /** Used for pushing starred contacts to the top of a times contacted list **/ 361 private static final HashMap<String, String> sStrequentStarredProjectionMap; 362 private static final HashMap<String, String> sStrequentFrequentProjectionMap; 363 /** Contains just the contacts vCard columns */ 364 private static final HashMap<String, String> sContactsVCardProjectionMap; 365 /** Contains just the raw contacts columns */ 366 private static final HashMap<String, String> sRawContactsProjectionMap; 367 /** Contains the columns from the raw contacts entity view*/ 368 private static final HashMap<String, String> sRawContactsEntityProjectionMap; 369 /** Contains columns from the data view */ 370 private static final HashMap<String, String> sDataProjectionMap; 371 /** Contains columns from the data view */ 372 private static final HashMap<String, String> sDistinctDataProjectionMap; 373 /** Contains the data and contacts columns, for joined tables */ 374 private static final HashMap<String, String> sPhoneLookupProjectionMap; 375 /** Contains the just the {@link Groups} columns */ 376 private static final HashMap<String, String> sGroupsProjectionMap; 377 /** Contains {@link Groups} columns along with summary details */ 378 private static final HashMap<String, String> sGroupsSummaryProjectionMap; 379 /** Contains the agg_exceptions columns */ 380 private static final HashMap<String, String> sAggregationExceptionsProjectionMap; 381 /** Contains the agg_exceptions columns */ 382 private static final HashMap<String, String> sSettingsProjectionMap; 383 /** Contains StatusUpdates columns */ 384 private static final HashMap<String, String> sStatusUpdatesProjectionMap; 385 /** Contains Live Folders columns */ 386 private static final HashMap<String, String> sLiveFoldersProjectionMap; 387 388 // where clause to update the status_updates table 389 private static final String WHERE_CLAUSE_FOR_STATUS_UPDATES_TABLE = 390 StatusUpdatesColumns.DATA_ID + " IN (SELECT Distinct " + StatusUpdates.DATA_ID + 391 " FROM " + Tables.STATUS_UPDATES + " LEFT OUTER JOIN " + Tables.PRESENCE + 392 " ON " + StatusUpdatesColumns.DATA_ID + " = " + StatusUpdates.DATA_ID + " WHERE "; 393 394 private static final String[] EMPTY_STRING_ARRAY = new String[0]; 395 396 /** 397 * Notification ID for failure to import contacts. 398 */ 399 private static final int LEGACY_IMPORT_FAILED_NOTIFICATION = 1; 400 401 /** Precompiled sql statement for setting a data record to the primary. */ 402 private SQLiteStatement mSetPrimaryStatement; 403 /** Precompiled sql statement for setting a data record to the super primary. */ 404 private SQLiteStatement mSetSuperPrimaryStatement; 405 /** Precompiled sql statement for updating a contact display name */ 406 private SQLiteStatement mRawContactDisplayNameUpdate; 407 /** Precompiled sql statement for updating an aggregated status update */ 408 private SQLiteStatement mLastStatusUpdate; 409 private SQLiteStatement mNameLookupInsert; 410 private SQLiteStatement mNameLookupDelete; 411 private SQLiteStatement mStatusUpdateAutoTimestamp; 412 private SQLiteStatement mStatusUpdateInsert; 413 private SQLiteStatement mStatusUpdateReplace; 414 private SQLiteStatement mStatusAttributionUpdate; 415 private SQLiteStatement mStatusUpdateDelete; 416 private SQLiteStatement mResetNameVerifiedForOtherRawContacts; 417 418 private long mMimeTypeIdEmail; 419 private long mMimeTypeIdIm; 420 private long mMimeTypeIdStructuredName; 421 private long mMimeTypeIdOrganization; 422 private long mMimeTypeIdNickname; 423 private long mMimeTypeIdPhone; 424 private StringBuilder mSb = new StringBuilder(); 425 private String[] mSelectionArgs1 = new String[1]; 426 private String[] mSelectionArgs2 = new String[2]; 427 private ArrayList<String> mSelectionArgs = Lists.newArrayList(); 428 429 private Account mAccount; 430 431 static { 432 // Contacts URI matching table 433 final UriMatcher matcher = sUriMatcher; matcher.addURI(ContactsContract.AUTHORITY, "contacts", CONTACTS)434 matcher.addURI(ContactsContract.AUTHORITY, "contacts", CONTACTS); matcher.addURI(ContactsContract.AUTHORITY, "contacts/#", CONTACTS_ID)435 matcher.addURI(ContactsContract.AUTHORITY, "contacts/#", CONTACTS_ID); matcher.addURI(ContactsContract.AUTHORITY, "contacts/#/data", CONTACTS_DATA)436 matcher.addURI(ContactsContract.AUTHORITY, "contacts/#/data", CONTACTS_DATA); matcher.addURI(ContactsContract.AUTHORITY, "contacts/#/suggestions", AGGREGATION_SUGGESTIONS)437 matcher.addURI(ContactsContract.AUTHORITY, "contacts/#/suggestions", 438 AGGREGATION_SUGGESTIONS); matcher.addURI(ContactsContract.AUTHORITY, "contacts/#/suggestions/*", AGGREGATION_SUGGESTIONS)439 matcher.addURI(ContactsContract.AUTHORITY, "contacts/#/suggestions/*", 440 AGGREGATION_SUGGESTIONS); matcher.addURI(ContactsContract.AUTHORITY, "contacts/#/photo", CONTACTS_PHOTO)441 matcher.addURI(ContactsContract.AUTHORITY, "contacts/#/photo", CONTACTS_PHOTO); matcher.addURI(ContactsContract.AUTHORITY, "contacts/filter/*", CONTACTS_FILTER)442 matcher.addURI(ContactsContract.AUTHORITY, "contacts/filter/*", CONTACTS_FILTER); matcher.addURI(ContactsContract.AUTHORITY, "contacts/lookup/*", CONTACTS_LOOKUP)443 matcher.addURI(ContactsContract.AUTHORITY, "contacts/lookup/*", CONTACTS_LOOKUP); matcher.addURI(ContactsContract.AUTHORITY, "contacts/lookup/*/#", CONTACTS_LOOKUP_ID)444 matcher.addURI(ContactsContract.AUTHORITY, "contacts/lookup/*/#", CONTACTS_LOOKUP_ID); matcher.addURI(ContactsContract.AUTHORITY, "contacts/as_vcard/*", CONTACTS_AS_VCARD)445 matcher.addURI(ContactsContract.AUTHORITY, "contacts/as_vcard/*", CONTACTS_AS_VCARD); matcher.addURI(ContactsContract.AUTHORITY, "contacts/as_multi_vcard/*", CONTACTS_AS_MULTI_VCARD)446 matcher.addURI(ContactsContract.AUTHORITY, "contacts/as_multi_vcard/*", 447 CONTACTS_AS_MULTI_VCARD); matcher.addURI(ContactsContract.AUTHORITY, "contacts/strequent/", CONTACTS_STREQUENT)448 matcher.addURI(ContactsContract.AUTHORITY, "contacts/strequent/", CONTACTS_STREQUENT); matcher.addURI(ContactsContract.AUTHORITY, "contacts/strequent/filter/*", CONTACTS_STREQUENT_FILTER)449 matcher.addURI(ContactsContract.AUTHORITY, "contacts/strequent/filter/*", 450 CONTACTS_STREQUENT_FILTER); matcher.addURI(ContactsContract.AUTHORITY, "contacts/group/*", CONTACTS_GROUP)451 matcher.addURI(ContactsContract.AUTHORITY, "contacts/group/*", CONTACTS_GROUP); 452 matcher.addURI(ContactsContract.AUTHORITY, "raw_contacts", RAW_CONTACTS)453 matcher.addURI(ContactsContract.AUTHORITY, "raw_contacts", RAW_CONTACTS); matcher.addURI(ContactsContract.AUTHORITY, "raw_contacts/#", RAW_CONTACTS_ID)454 matcher.addURI(ContactsContract.AUTHORITY, "raw_contacts/#", RAW_CONTACTS_ID); matcher.addURI(ContactsContract.AUTHORITY, "raw_contacts/#/data", RAW_CONTACTS_DATA)455 matcher.addURI(ContactsContract.AUTHORITY, "raw_contacts/#/data", RAW_CONTACTS_DATA); matcher.addURI(ContactsContract.AUTHORITY, "raw_contacts/#/entity", RAW_CONTACT_ENTITY_ID)456 matcher.addURI(ContactsContract.AUTHORITY, "raw_contacts/#/entity", RAW_CONTACT_ENTITY_ID); 457 matcher.addURI(ContactsContract.AUTHORITY, "raw_contact_entities", RAW_CONTACT_ENTITIES)458 matcher.addURI(ContactsContract.AUTHORITY, "raw_contact_entities", RAW_CONTACT_ENTITIES); 459 matcher.addURI(ContactsContract.AUTHORITY, "data", DATA)460 matcher.addURI(ContactsContract.AUTHORITY, "data", DATA); matcher.addURI(ContactsContract.AUTHORITY, "data/#", DATA_ID)461 matcher.addURI(ContactsContract.AUTHORITY, "data/#", DATA_ID); matcher.addURI(ContactsContract.AUTHORITY, "data/phones", PHONES)462 matcher.addURI(ContactsContract.AUTHORITY, "data/phones", PHONES); matcher.addURI(ContactsContract.AUTHORITY, "data/phones/#", PHONES_ID)463 matcher.addURI(ContactsContract.AUTHORITY, "data/phones/#", PHONES_ID); matcher.addURI(ContactsContract.AUTHORITY, "data/phones/filter", PHONES_FILTER)464 matcher.addURI(ContactsContract.AUTHORITY, "data/phones/filter", PHONES_FILTER); matcher.addURI(ContactsContract.AUTHORITY, "data/phones/filter/*", PHONES_FILTER)465 matcher.addURI(ContactsContract.AUTHORITY, "data/phones/filter/*", PHONES_FILTER); matcher.addURI(ContactsContract.AUTHORITY, "data/emails", EMAILS)466 matcher.addURI(ContactsContract.AUTHORITY, "data/emails", EMAILS); matcher.addURI(ContactsContract.AUTHORITY, "data/emails/#", EMAILS_ID)467 matcher.addURI(ContactsContract.AUTHORITY, "data/emails/#", EMAILS_ID); matcher.addURI(ContactsContract.AUTHORITY, "data/emails/lookup/*", EMAILS_LOOKUP)468 matcher.addURI(ContactsContract.AUTHORITY, "data/emails/lookup/*", EMAILS_LOOKUP); matcher.addURI(ContactsContract.AUTHORITY, "data/emails/filter", EMAILS_FILTER)469 matcher.addURI(ContactsContract.AUTHORITY, "data/emails/filter", EMAILS_FILTER); matcher.addURI(ContactsContract.AUTHORITY, "data/emails/filter/*", EMAILS_FILTER)470 matcher.addURI(ContactsContract.AUTHORITY, "data/emails/filter/*", EMAILS_FILTER); matcher.addURI(ContactsContract.AUTHORITY, "data/postals", POSTALS)471 matcher.addURI(ContactsContract.AUTHORITY, "data/postals", POSTALS); matcher.addURI(ContactsContract.AUTHORITY, "data/postals/#", POSTALS_ID)472 matcher.addURI(ContactsContract.AUTHORITY, "data/postals/#", POSTALS_ID); 473 matcher.addURI(ContactsContract.AUTHORITY, "groups", GROUPS)474 matcher.addURI(ContactsContract.AUTHORITY, "groups", GROUPS); matcher.addURI(ContactsContract.AUTHORITY, "groups/#", GROUPS_ID)475 matcher.addURI(ContactsContract.AUTHORITY, "groups/#", GROUPS_ID); matcher.addURI(ContactsContract.AUTHORITY, "groups_summary", GROUPS_SUMMARY)476 matcher.addURI(ContactsContract.AUTHORITY, "groups_summary", GROUPS_SUMMARY); 477 matcher.addURI(ContactsContract.AUTHORITY, SyncStateContentProviderHelper.PATH, SYNCSTATE)478 matcher.addURI(ContactsContract.AUTHORITY, SyncStateContentProviderHelper.PATH, SYNCSTATE); matcher.addURI(ContactsContract.AUTHORITY, SyncStateContentProviderHelper.PATH + "/#", SYNCSTATE_ID)479 matcher.addURI(ContactsContract.AUTHORITY, SyncStateContentProviderHelper.PATH + "/#", 480 SYNCSTATE_ID); 481 matcher.addURI(ContactsContract.AUTHORITY, "phone_lookup/*", PHONE_LOOKUP)482 matcher.addURI(ContactsContract.AUTHORITY, "phone_lookup/*", PHONE_LOOKUP); matcher.addURI(ContactsContract.AUTHORITY, "aggregation_exceptions", AGGREGATION_EXCEPTIONS)483 matcher.addURI(ContactsContract.AUTHORITY, "aggregation_exceptions", 484 AGGREGATION_EXCEPTIONS); matcher.addURI(ContactsContract.AUTHORITY, "aggregation_exceptions/*", AGGREGATION_EXCEPTION_ID)485 matcher.addURI(ContactsContract.AUTHORITY, "aggregation_exceptions/*", 486 AGGREGATION_EXCEPTION_ID); 487 matcher.addURI(ContactsContract.AUTHORITY, "settings", SETTINGS)488 matcher.addURI(ContactsContract.AUTHORITY, "settings", SETTINGS); 489 matcher.addURI(ContactsContract.AUTHORITY, "status_updates", STATUS_UPDATES)490 matcher.addURI(ContactsContract.AUTHORITY, "status_updates", STATUS_UPDATES); matcher.addURI(ContactsContract.AUTHORITY, "status_updates/#", STATUS_UPDATES_ID)491 matcher.addURI(ContactsContract.AUTHORITY, "status_updates/#", STATUS_UPDATES_ID); 492 matcher.addURI(ContactsContract.AUTHORITY, SearchManager.SUGGEST_URI_PATH_QUERY, SEARCH_SUGGESTIONS)493 matcher.addURI(ContactsContract.AUTHORITY, SearchManager.SUGGEST_URI_PATH_QUERY, 494 SEARCH_SUGGESTIONS); matcher.addURI(ContactsContract.AUTHORITY, SearchManager.SUGGEST_URI_PATH_QUERY + "/*", SEARCH_SUGGESTIONS)495 matcher.addURI(ContactsContract.AUTHORITY, SearchManager.SUGGEST_URI_PATH_QUERY + "/*", 496 SEARCH_SUGGESTIONS); matcher.addURI(ContactsContract.AUTHORITY, SearchManager.SUGGEST_URI_PATH_SHORTCUT + "/*", SEARCH_SHORTCUT)497 matcher.addURI(ContactsContract.AUTHORITY, SearchManager.SUGGEST_URI_PATH_SHORTCUT + "/*", 498 SEARCH_SHORTCUT); 499 matcher.addURI(ContactsContract.AUTHORITY, "live_folders/contacts", LIVE_FOLDERS_CONTACTS)500 matcher.addURI(ContactsContract.AUTHORITY, "live_folders/contacts", 501 LIVE_FOLDERS_CONTACTS); matcher.addURI(ContactsContract.AUTHORITY, "live_folders/contacts/*", LIVE_FOLDERS_CONTACTS_GROUP_NAME)502 matcher.addURI(ContactsContract.AUTHORITY, "live_folders/contacts/*", 503 LIVE_FOLDERS_CONTACTS_GROUP_NAME); matcher.addURI(ContactsContract.AUTHORITY, "live_folders/contacts_with_phones", LIVE_FOLDERS_CONTACTS_WITH_PHONES)504 matcher.addURI(ContactsContract.AUTHORITY, "live_folders/contacts_with_phones", 505 LIVE_FOLDERS_CONTACTS_WITH_PHONES); matcher.addURI(ContactsContract.AUTHORITY, "live_folders/favorites", LIVE_FOLDERS_CONTACTS_FAVORITES)506 matcher.addURI(ContactsContract.AUTHORITY, "live_folders/favorites", 507 LIVE_FOLDERS_CONTACTS_FAVORITES); 508 matcher.addURI(ContactsContract.AUTHORITY, "provider_status", PROVIDER_STATUS)509 matcher.addURI(ContactsContract.AUTHORITY, "provider_status", PROVIDER_STATUS); 510 } 511 512 static { 513 sCountProjectionMap = new HashMap<String, String>(); sCountProjectionMap.put(BaseColumns._COUNT, "COUNT(*)")514 sCountProjectionMap.put(BaseColumns._COUNT, "COUNT(*)"); 515 516 sContactsProjectionMap = new HashMap<String, String>(); sContactsProjectionMap.put(Contacts._ID, Contacts._ID)517 sContactsProjectionMap.put(Contacts._ID, Contacts._ID); sContactsProjectionMap.put(Contacts.DISPLAY_NAME, Contacts.DISPLAY_NAME_PRIMARY)518 sContactsProjectionMap.put(Contacts.DISPLAY_NAME, Contacts.DISPLAY_NAME_PRIMARY); sContactsProjectionMap.put(Contacts.DISPLAY_NAME_ALTERNATIVE, Contacts.DISPLAY_NAME_ALTERNATIVE)519 sContactsProjectionMap.put(Contacts.DISPLAY_NAME_ALTERNATIVE, 520 Contacts.DISPLAY_NAME_ALTERNATIVE); sContactsProjectionMap.put(Contacts.DISPLAY_NAME_SOURCE, Contacts.DISPLAY_NAME_SOURCE)521 sContactsProjectionMap.put(Contacts.DISPLAY_NAME_SOURCE, Contacts.DISPLAY_NAME_SOURCE); sContactsProjectionMap.put(Contacts.PHONETIC_NAME, Contacts.PHONETIC_NAME)522 sContactsProjectionMap.put(Contacts.PHONETIC_NAME, Contacts.PHONETIC_NAME); sContactsProjectionMap.put(Contacts.PHONETIC_NAME_STYLE, Contacts.PHONETIC_NAME_STYLE)523 sContactsProjectionMap.put(Contacts.PHONETIC_NAME_STYLE, Contacts.PHONETIC_NAME_STYLE); sContactsProjectionMap.put(Contacts.SORT_KEY_PRIMARY, Contacts.SORT_KEY_PRIMARY)524 sContactsProjectionMap.put(Contacts.SORT_KEY_PRIMARY, Contacts.SORT_KEY_PRIMARY); sContactsProjectionMap.put(Contacts.SORT_KEY_ALTERNATIVE, Contacts.SORT_KEY_ALTERNATIVE)525 sContactsProjectionMap.put(Contacts.SORT_KEY_ALTERNATIVE, Contacts.SORT_KEY_ALTERNATIVE); sContactsProjectionMap.put(Contacts.LAST_TIME_CONTACTED, Contacts.LAST_TIME_CONTACTED)526 sContactsProjectionMap.put(Contacts.LAST_TIME_CONTACTED, Contacts.LAST_TIME_CONTACTED); sContactsProjectionMap.put(Contacts.TIMES_CONTACTED, Contacts.TIMES_CONTACTED)527 sContactsProjectionMap.put(Contacts.TIMES_CONTACTED, Contacts.TIMES_CONTACTED); sContactsProjectionMap.put(Contacts.STARRED, Contacts.STARRED)528 sContactsProjectionMap.put(Contacts.STARRED, Contacts.STARRED); sContactsProjectionMap.put(Contacts.IN_VISIBLE_GROUP, Contacts.IN_VISIBLE_GROUP)529 sContactsProjectionMap.put(Contacts.IN_VISIBLE_GROUP, Contacts.IN_VISIBLE_GROUP); sContactsProjectionMap.put(Contacts.PHOTO_ID, Contacts.PHOTO_ID)530 sContactsProjectionMap.put(Contacts.PHOTO_ID, Contacts.PHOTO_ID); sContactsProjectionMap.put(Contacts.CUSTOM_RINGTONE, Contacts.CUSTOM_RINGTONE)531 sContactsProjectionMap.put(Contacts.CUSTOM_RINGTONE, Contacts.CUSTOM_RINGTONE); sContactsProjectionMap.put(Contacts.HAS_PHONE_NUMBER, Contacts.HAS_PHONE_NUMBER)532 sContactsProjectionMap.put(Contacts.HAS_PHONE_NUMBER, Contacts.HAS_PHONE_NUMBER); sContactsProjectionMap.put(Contacts.SEND_TO_VOICEMAIL, Contacts.SEND_TO_VOICEMAIL)533 sContactsProjectionMap.put(Contacts.SEND_TO_VOICEMAIL, Contacts.SEND_TO_VOICEMAIL); sContactsProjectionMap.put(Contacts.LOOKUP_KEY, Contacts.LOOKUP_KEY)534 sContactsProjectionMap.put(Contacts.LOOKUP_KEY, Contacts.LOOKUP_KEY); 535 536 // Handle projections for Contacts-level statuses addProjection(sContactsProjectionMap, Contacts.CONTACT_PRESENCE, Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.PRESENCE)537 addProjection(sContactsProjectionMap, Contacts.CONTACT_PRESENCE, 538 Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.PRESENCE); addProjection(sContactsProjectionMap, Contacts.CONTACT_CHAT_CAPABILITY, Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY)539 addProjection(sContactsProjectionMap, Contacts.CONTACT_CHAT_CAPABILITY, 540 Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY); addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS, ContactsStatusUpdatesColumns.CONCRETE_STATUS)541 addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS, 542 ContactsStatusUpdatesColumns.CONCRETE_STATUS); addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS_TIMESTAMP, ContactsStatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP)543 addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS_TIMESTAMP, 544 ContactsStatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP); addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS_RES_PACKAGE, ContactsStatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE)545 addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS_RES_PACKAGE, 546 ContactsStatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE); addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS_LABEL, ContactsStatusUpdatesColumns.CONCRETE_STATUS_LABEL)547 addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS_LABEL, 548 ContactsStatusUpdatesColumns.CONCRETE_STATUS_LABEL); addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS_ICON, ContactsStatusUpdatesColumns.CONCRETE_STATUS_ICON)549 addProjection(sContactsProjectionMap, Contacts.CONTACT_STATUS_ICON, 550 ContactsStatusUpdatesColumns.CONCRETE_STATUS_ICON); 551 552 sContactsProjectionWithSnippetMap = new HashMap<String, String>(); 553 sContactsProjectionWithSnippetMap.putAll(sContactsProjectionMap); sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_MIMETYPE, SearchSnippetColumns.SNIPPET_MIMETYPE)554 sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_MIMETYPE, 555 SearchSnippetColumns.SNIPPET_MIMETYPE); sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA_ID, SearchSnippetColumns.SNIPPET_DATA_ID)556 sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA_ID, 557 SearchSnippetColumns.SNIPPET_DATA_ID); sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA1, SearchSnippetColumns.SNIPPET_DATA1)558 sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA1, 559 SearchSnippetColumns.SNIPPET_DATA1); sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA2, SearchSnippetColumns.SNIPPET_DATA2)560 sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA2, 561 SearchSnippetColumns.SNIPPET_DATA2); sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA3, SearchSnippetColumns.SNIPPET_DATA3)562 sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA3, 563 SearchSnippetColumns.SNIPPET_DATA3); sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA4, SearchSnippetColumns.SNIPPET_DATA4)564 sContactsProjectionWithSnippetMap.put(SearchSnippetColumns.SNIPPET_DATA4, 565 SearchSnippetColumns.SNIPPET_DATA4); 566 567 sStrequentStarredProjectionMap = new HashMap<String, String>(sContactsProjectionMap); sStrequentStarredProjectionMap.put(TIMES_CONTACED_SORT_COLUMN, Long.MAX_VALUE + " AS " + TIMES_CONTACED_SORT_COLUMN)568 sStrequentStarredProjectionMap.put(TIMES_CONTACED_SORT_COLUMN, 569 Long.MAX_VALUE + " AS " + TIMES_CONTACED_SORT_COLUMN); 570 571 sStrequentFrequentProjectionMap = new HashMap<String, String>(sContactsProjectionMap); sStrequentFrequentProjectionMap.put(TIMES_CONTACED_SORT_COLUMN, Contacts.TIMES_CONTACTED + " AS " + TIMES_CONTACED_SORT_COLUMN)572 sStrequentFrequentProjectionMap.put(TIMES_CONTACED_SORT_COLUMN, 573 Contacts.TIMES_CONTACTED + " AS " + TIMES_CONTACED_SORT_COLUMN); 574 575 sContactsVCardProjectionMap = Maps.newHashMap(); sContactsVCardProjectionMap.put(OpenableColumns.DISPLAY_NAME, Contacts.DISPLAY_NAME + " || '.vcf' AS " + OpenableColumns.DISPLAY_NAME)576 sContactsVCardProjectionMap.put(OpenableColumns.DISPLAY_NAME, Contacts.DISPLAY_NAME 577 + " || '.vcf' AS " + OpenableColumns.DISPLAY_NAME); sContactsVCardProjectionMap.put(OpenableColumns.SIZE, "NULL AS " + OpenableColumns.SIZE)578 sContactsVCardProjectionMap.put(OpenableColumns.SIZE, "NULL AS " + OpenableColumns.SIZE); 579 580 sRawContactsProjectionMap = new HashMap<String, String>(); sRawContactsProjectionMap.put(RawContacts._ID, RawContacts._ID)581 sRawContactsProjectionMap.put(RawContacts._ID, RawContacts._ID); sRawContactsProjectionMap.put(RawContacts.CONTACT_ID, RawContacts.CONTACT_ID)582 sRawContactsProjectionMap.put(RawContacts.CONTACT_ID, RawContacts.CONTACT_ID); sRawContactsProjectionMap.put(RawContacts.ACCOUNT_NAME, RawContacts.ACCOUNT_NAME)583 sRawContactsProjectionMap.put(RawContacts.ACCOUNT_NAME, RawContacts.ACCOUNT_NAME); sRawContactsProjectionMap.put(RawContacts.ACCOUNT_TYPE, RawContacts.ACCOUNT_TYPE)584 sRawContactsProjectionMap.put(RawContacts.ACCOUNT_TYPE, RawContacts.ACCOUNT_TYPE); sRawContactsProjectionMap.put(RawContacts.SOURCE_ID, RawContacts.SOURCE_ID)585 sRawContactsProjectionMap.put(RawContacts.SOURCE_ID, RawContacts.SOURCE_ID); sRawContactsProjectionMap.put(RawContacts.VERSION, RawContacts.VERSION)586 sRawContactsProjectionMap.put(RawContacts.VERSION, RawContacts.VERSION); sRawContactsProjectionMap.put(RawContacts.DIRTY, RawContacts.DIRTY)587 sRawContactsProjectionMap.put(RawContacts.DIRTY, RawContacts.DIRTY); sRawContactsProjectionMap.put(RawContacts.DELETED, RawContacts.DELETED)588 sRawContactsProjectionMap.put(RawContacts.DELETED, RawContacts.DELETED); sRawContactsProjectionMap.put(RawContacts.DISPLAY_NAME_PRIMARY, RawContacts.DISPLAY_NAME_PRIMARY)589 sRawContactsProjectionMap.put(RawContacts.DISPLAY_NAME_PRIMARY, 590 RawContacts.DISPLAY_NAME_PRIMARY); sRawContactsProjectionMap.put(RawContacts.DISPLAY_NAME_ALTERNATIVE, RawContacts.DISPLAY_NAME_ALTERNATIVE)591 sRawContactsProjectionMap.put(RawContacts.DISPLAY_NAME_ALTERNATIVE, 592 RawContacts.DISPLAY_NAME_ALTERNATIVE); sRawContactsProjectionMap.put(RawContacts.DISPLAY_NAME_SOURCE, RawContacts.DISPLAY_NAME_SOURCE)593 sRawContactsProjectionMap.put(RawContacts.DISPLAY_NAME_SOURCE, 594 RawContacts.DISPLAY_NAME_SOURCE); sRawContactsProjectionMap.put(RawContacts.PHONETIC_NAME, RawContacts.PHONETIC_NAME)595 sRawContactsProjectionMap.put(RawContacts.PHONETIC_NAME, 596 RawContacts.PHONETIC_NAME); sRawContactsProjectionMap.put(RawContacts.PHONETIC_NAME_STYLE, RawContacts.PHONETIC_NAME_STYLE)597 sRawContactsProjectionMap.put(RawContacts.PHONETIC_NAME_STYLE, 598 RawContacts.PHONETIC_NAME_STYLE); sRawContactsProjectionMap.put(RawContacts.NAME_VERIFIED, RawContacts.NAME_VERIFIED)599 sRawContactsProjectionMap.put(RawContacts.NAME_VERIFIED, 600 RawContacts.NAME_VERIFIED); sRawContactsProjectionMap.put(RawContacts.SORT_KEY_PRIMARY, RawContacts.SORT_KEY_PRIMARY)601 sRawContactsProjectionMap.put(RawContacts.SORT_KEY_PRIMARY, 602 RawContacts.SORT_KEY_PRIMARY); sRawContactsProjectionMap.put(RawContacts.SORT_KEY_ALTERNATIVE, RawContacts.SORT_KEY_ALTERNATIVE)603 sRawContactsProjectionMap.put(RawContacts.SORT_KEY_ALTERNATIVE, 604 RawContacts.SORT_KEY_ALTERNATIVE); sRawContactsProjectionMap.put(RawContacts.TIMES_CONTACTED, RawContacts.TIMES_CONTACTED)605 sRawContactsProjectionMap.put(RawContacts.TIMES_CONTACTED, RawContacts.TIMES_CONTACTED); sRawContactsProjectionMap.put(RawContacts.LAST_TIME_CONTACTED, RawContacts.LAST_TIME_CONTACTED)606 sRawContactsProjectionMap.put(RawContacts.LAST_TIME_CONTACTED, 607 RawContacts.LAST_TIME_CONTACTED); sRawContactsProjectionMap.put(RawContacts.CUSTOM_RINGTONE, RawContacts.CUSTOM_RINGTONE)608 sRawContactsProjectionMap.put(RawContacts.CUSTOM_RINGTONE, RawContacts.CUSTOM_RINGTONE); sRawContactsProjectionMap.put(RawContacts.SEND_TO_VOICEMAIL, RawContacts.SEND_TO_VOICEMAIL)609 sRawContactsProjectionMap.put(RawContacts.SEND_TO_VOICEMAIL, RawContacts.SEND_TO_VOICEMAIL); sRawContactsProjectionMap.put(RawContacts.STARRED, RawContacts.STARRED)610 sRawContactsProjectionMap.put(RawContacts.STARRED, RawContacts.STARRED); sRawContactsProjectionMap.put(RawContacts.AGGREGATION_MODE, RawContacts.AGGREGATION_MODE)611 sRawContactsProjectionMap.put(RawContacts.AGGREGATION_MODE, RawContacts.AGGREGATION_MODE); sRawContactsProjectionMap.put(RawContacts.SYNC1, RawContacts.SYNC1)612 sRawContactsProjectionMap.put(RawContacts.SYNC1, RawContacts.SYNC1); sRawContactsProjectionMap.put(RawContacts.SYNC2, RawContacts.SYNC2)613 sRawContactsProjectionMap.put(RawContacts.SYNC2, RawContacts.SYNC2); sRawContactsProjectionMap.put(RawContacts.SYNC3, RawContacts.SYNC3)614 sRawContactsProjectionMap.put(RawContacts.SYNC3, RawContacts.SYNC3); sRawContactsProjectionMap.put(RawContacts.SYNC4, RawContacts.SYNC4)615 sRawContactsProjectionMap.put(RawContacts.SYNC4, RawContacts.SYNC4); 616 617 sDataProjectionMap = new HashMap<String, String>(); sDataProjectionMap.put(Data._ID, Data._ID)618 sDataProjectionMap.put(Data._ID, Data._ID); sDataProjectionMap.put(Data.RAW_CONTACT_ID, Data.RAW_CONTACT_ID)619 sDataProjectionMap.put(Data.RAW_CONTACT_ID, Data.RAW_CONTACT_ID); sDataProjectionMap.put(Data.DATA_VERSION, Data.DATA_VERSION)620 sDataProjectionMap.put(Data.DATA_VERSION, Data.DATA_VERSION); sDataProjectionMap.put(Data.IS_PRIMARY, Data.IS_PRIMARY)621 sDataProjectionMap.put(Data.IS_PRIMARY, Data.IS_PRIMARY); sDataProjectionMap.put(Data.IS_SUPER_PRIMARY, Data.IS_SUPER_PRIMARY)622 sDataProjectionMap.put(Data.IS_SUPER_PRIMARY, Data.IS_SUPER_PRIMARY); sDataProjectionMap.put(Data.RES_PACKAGE, Data.RES_PACKAGE)623 sDataProjectionMap.put(Data.RES_PACKAGE, Data.RES_PACKAGE); sDataProjectionMap.put(Data.MIMETYPE, Data.MIMETYPE)624 sDataProjectionMap.put(Data.MIMETYPE, Data.MIMETYPE); sDataProjectionMap.put(Data.DATA1, Data.DATA1)625 sDataProjectionMap.put(Data.DATA1, Data.DATA1); sDataProjectionMap.put(Data.DATA2, Data.DATA2)626 sDataProjectionMap.put(Data.DATA2, Data.DATA2); sDataProjectionMap.put(Data.DATA3, Data.DATA3)627 sDataProjectionMap.put(Data.DATA3, Data.DATA3); sDataProjectionMap.put(Data.DATA4, Data.DATA4)628 sDataProjectionMap.put(Data.DATA4, Data.DATA4); sDataProjectionMap.put(Data.DATA5, Data.DATA5)629 sDataProjectionMap.put(Data.DATA5, Data.DATA5); sDataProjectionMap.put(Data.DATA6, Data.DATA6)630 sDataProjectionMap.put(Data.DATA6, Data.DATA6); sDataProjectionMap.put(Data.DATA7, Data.DATA7)631 sDataProjectionMap.put(Data.DATA7, Data.DATA7); sDataProjectionMap.put(Data.DATA8, Data.DATA8)632 sDataProjectionMap.put(Data.DATA8, Data.DATA8); sDataProjectionMap.put(Data.DATA9, Data.DATA9)633 sDataProjectionMap.put(Data.DATA9, Data.DATA9); sDataProjectionMap.put(Data.DATA10, Data.DATA10)634 sDataProjectionMap.put(Data.DATA10, Data.DATA10); sDataProjectionMap.put(Data.DATA11, Data.DATA11)635 sDataProjectionMap.put(Data.DATA11, Data.DATA11); sDataProjectionMap.put(Data.DATA12, Data.DATA12)636 sDataProjectionMap.put(Data.DATA12, Data.DATA12); sDataProjectionMap.put(Data.DATA13, Data.DATA13)637 sDataProjectionMap.put(Data.DATA13, Data.DATA13); sDataProjectionMap.put(Data.DATA14, Data.DATA14)638 sDataProjectionMap.put(Data.DATA14, Data.DATA14); sDataProjectionMap.put(Data.DATA15, Data.DATA15)639 sDataProjectionMap.put(Data.DATA15, Data.DATA15); sDataProjectionMap.put(Data.SYNC1, Data.SYNC1)640 sDataProjectionMap.put(Data.SYNC1, Data.SYNC1); sDataProjectionMap.put(Data.SYNC2, Data.SYNC2)641 sDataProjectionMap.put(Data.SYNC2, Data.SYNC2); sDataProjectionMap.put(Data.SYNC3, Data.SYNC3)642 sDataProjectionMap.put(Data.SYNC3, Data.SYNC3); sDataProjectionMap.put(Data.SYNC4, Data.SYNC4)643 sDataProjectionMap.put(Data.SYNC4, Data.SYNC4); sDataProjectionMap.put(Data.CONTACT_ID, Data.CONTACT_ID)644 sDataProjectionMap.put(Data.CONTACT_ID, Data.CONTACT_ID); sDataProjectionMap.put(RawContacts.ACCOUNT_NAME, RawContacts.ACCOUNT_NAME)645 sDataProjectionMap.put(RawContacts.ACCOUNT_NAME, RawContacts.ACCOUNT_NAME); sDataProjectionMap.put(RawContacts.ACCOUNT_TYPE, RawContacts.ACCOUNT_TYPE)646 sDataProjectionMap.put(RawContacts.ACCOUNT_TYPE, RawContacts.ACCOUNT_TYPE); sDataProjectionMap.put(RawContacts.SOURCE_ID, RawContacts.SOURCE_ID)647 sDataProjectionMap.put(RawContacts.SOURCE_ID, RawContacts.SOURCE_ID); sDataProjectionMap.put(RawContacts.VERSION, RawContacts.VERSION)648 sDataProjectionMap.put(RawContacts.VERSION, RawContacts.VERSION); sDataProjectionMap.put(RawContacts.DIRTY, RawContacts.DIRTY)649 sDataProjectionMap.put(RawContacts.DIRTY, RawContacts.DIRTY); sDataProjectionMap.put(RawContacts.NAME_VERIFIED, RawContacts.NAME_VERIFIED)650 sDataProjectionMap.put(RawContacts.NAME_VERIFIED, RawContacts.NAME_VERIFIED); sDataProjectionMap.put(Contacts.LOOKUP_KEY, Contacts.LOOKUP_KEY)651 sDataProjectionMap.put(Contacts.LOOKUP_KEY, Contacts.LOOKUP_KEY); sDataProjectionMap.put(Contacts.DISPLAY_NAME, Contacts.DISPLAY_NAME)652 sDataProjectionMap.put(Contacts.DISPLAY_NAME, Contacts.DISPLAY_NAME); sDataProjectionMap.put(Contacts.DISPLAY_NAME_ALTERNATIVE, Contacts.DISPLAY_NAME_ALTERNATIVE)653 sDataProjectionMap.put(Contacts.DISPLAY_NAME_ALTERNATIVE, 654 Contacts.DISPLAY_NAME_ALTERNATIVE); sDataProjectionMap.put(Contacts.DISPLAY_NAME_SOURCE, Contacts.DISPLAY_NAME_SOURCE)655 sDataProjectionMap.put(Contacts.DISPLAY_NAME_SOURCE, Contacts.DISPLAY_NAME_SOURCE); sDataProjectionMap.put(Contacts.PHONETIC_NAME, Contacts.PHONETIC_NAME)656 sDataProjectionMap.put(Contacts.PHONETIC_NAME, Contacts.PHONETIC_NAME); sDataProjectionMap.put(Contacts.PHONETIC_NAME_STYLE, Contacts.PHONETIC_NAME_STYLE)657 sDataProjectionMap.put(Contacts.PHONETIC_NAME_STYLE, Contacts.PHONETIC_NAME_STYLE); sDataProjectionMap.put(Contacts.SORT_KEY_PRIMARY, Contacts.SORT_KEY_PRIMARY)658 sDataProjectionMap.put(Contacts.SORT_KEY_PRIMARY, Contacts.SORT_KEY_PRIMARY); sDataProjectionMap.put(Contacts.SORT_KEY_ALTERNATIVE, Contacts.SORT_KEY_ALTERNATIVE)659 sDataProjectionMap.put(Contacts.SORT_KEY_ALTERNATIVE, Contacts.SORT_KEY_ALTERNATIVE); sDataProjectionMap.put(Contacts.CUSTOM_RINGTONE, Contacts.CUSTOM_RINGTONE)660 sDataProjectionMap.put(Contacts.CUSTOM_RINGTONE, Contacts.CUSTOM_RINGTONE); sDataProjectionMap.put(Contacts.SEND_TO_VOICEMAIL, Contacts.SEND_TO_VOICEMAIL)661 sDataProjectionMap.put(Contacts.SEND_TO_VOICEMAIL, Contacts.SEND_TO_VOICEMAIL); sDataProjectionMap.put(Contacts.LAST_TIME_CONTACTED, Contacts.LAST_TIME_CONTACTED)662 sDataProjectionMap.put(Contacts.LAST_TIME_CONTACTED, Contacts.LAST_TIME_CONTACTED); sDataProjectionMap.put(Contacts.TIMES_CONTACTED, Contacts.TIMES_CONTACTED)663 sDataProjectionMap.put(Contacts.TIMES_CONTACTED, Contacts.TIMES_CONTACTED); sDataProjectionMap.put(Contacts.STARRED, Contacts.STARRED)664 sDataProjectionMap.put(Contacts.STARRED, Contacts.STARRED); sDataProjectionMap.put(Contacts.PHOTO_ID, Contacts.PHOTO_ID)665 sDataProjectionMap.put(Contacts.PHOTO_ID, Contacts.PHOTO_ID); sDataProjectionMap.put(Contacts.IN_VISIBLE_GROUP, Contacts.IN_VISIBLE_GROUP)666 sDataProjectionMap.put(Contacts.IN_VISIBLE_GROUP, Contacts.IN_VISIBLE_GROUP); sDataProjectionMap.put(Contacts.NAME_RAW_CONTACT_ID, Contacts.NAME_RAW_CONTACT_ID)667 sDataProjectionMap.put(Contacts.NAME_RAW_CONTACT_ID, Contacts.NAME_RAW_CONTACT_ID); sDataProjectionMap.put(GroupMembership.GROUP_SOURCE_ID, GroupMembership.GROUP_SOURCE_ID)668 sDataProjectionMap.put(GroupMembership.GROUP_SOURCE_ID, GroupMembership.GROUP_SOURCE_ID); 669 670 HashMap<String, String> columns; 671 columns = new HashMap<String, String>(); columns.put(RawContacts._ID, RawContacts._ID)672 columns.put(RawContacts._ID, RawContacts._ID); columns.put(RawContacts.CONTACT_ID, RawContacts.CONTACT_ID)673 columns.put(RawContacts.CONTACT_ID, RawContacts.CONTACT_ID); columns.put(RawContacts.ACCOUNT_NAME, RawContacts.ACCOUNT_NAME)674 columns.put(RawContacts.ACCOUNT_NAME, RawContacts.ACCOUNT_NAME); columns.put(RawContacts.ACCOUNT_TYPE, RawContacts.ACCOUNT_TYPE)675 columns.put(RawContacts.ACCOUNT_TYPE, RawContacts.ACCOUNT_TYPE); columns.put(RawContacts.SOURCE_ID, RawContacts.SOURCE_ID)676 columns.put(RawContacts.SOURCE_ID, RawContacts.SOURCE_ID); columns.put(RawContacts.VERSION, RawContacts.VERSION)677 columns.put(RawContacts.VERSION, RawContacts.VERSION); columns.put(RawContacts.DIRTY, RawContacts.DIRTY)678 columns.put(RawContacts.DIRTY, RawContacts.DIRTY); columns.put(RawContacts.DELETED, RawContacts.DELETED)679 columns.put(RawContacts.DELETED, RawContacts.DELETED); columns.put(RawContacts.IS_RESTRICTED, RawContacts.IS_RESTRICTED)680 columns.put(RawContacts.IS_RESTRICTED, RawContacts.IS_RESTRICTED); columns.put(RawContacts.SYNC1, RawContacts.SYNC1)681 columns.put(RawContacts.SYNC1, RawContacts.SYNC1); columns.put(RawContacts.SYNC2, RawContacts.SYNC2)682 columns.put(RawContacts.SYNC2, RawContacts.SYNC2); columns.put(RawContacts.SYNC3, RawContacts.SYNC3)683 columns.put(RawContacts.SYNC3, RawContacts.SYNC3); columns.put(RawContacts.SYNC4, RawContacts.SYNC4)684 columns.put(RawContacts.SYNC4, RawContacts.SYNC4); columns.put(RawContacts.NAME_VERIFIED, RawContacts.NAME_VERIFIED)685 columns.put(RawContacts.NAME_VERIFIED, RawContacts.NAME_VERIFIED); columns.put(Data.RES_PACKAGE, Data.RES_PACKAGE)686 columns.put(Data.RES_PACKAGE, Data.RES_PACKAGE); columns.put(Data.MIMETYPE, Data.MIMETYPE)687 columns.put(Data.MIMETYPE, Data.MIMETYPE); columns.put(Data.DATA1, Data.DATA1)688 columns.put(Data.DATA1, Data.DATA1); columns.put(Data.DATA2, Data.DATA2)689 columns.put(Data.DATA2, Data.DATA2); columns.put(Data.DATA3, Data.DATA3)690 columns.put(Data.DATA3, Data.DATA3); columns.put(Data.DATA4, Data.DATA4)691 columns.put(Data.DATA4, Data.DATA4); columns.put(Data.DATA5, Data.DATA5)692 columns.put(Data.DATA5, Data.DATA5); columns.put(Data.DATA6, Data.DATA6)693 columns.put(Data.DATA6, Data.DATA6); columns.put(Data.DATA7, Data.DATA7)694 columns.put(Data.DATA7, Data.DATA7); columns.put(Data.DATA8, Data.DATA8)695 columns.put(Data.DATA8, Data.DATA8); columns.put(Data.DATA9, Data.DATA9)696 columns.put(Data.DATA9, Data.DATA9); columns.put(Data.DATA10, Data.DATA10)697 columns.put(Data.DATA10, Data.DATA10); columns.put(Data.DATA11, Data.DATA11)698 columns.put(Data.DATA11, Data.DATA11); columns.put(Data.DATA12, Data.DATA12)699 columns.put(Data.DATA12, Data.DATA12); columns.put(Data.DATA13, Data.DATA13)700 columns.put(Data.DATA13, Data.DATA13); columns.put(Data.DATA14, Data.DATA14)701 columns.put(Data.DATA14, Data.DATA14); columns.put(Data.DATA15, Data.DATA15)702 columns.put(Data.DATA15, Data.DATA15); columns.put(Data.SYNC1, Data.SYNC1)703 columns.put(Data.SYNC1, Data.SYNC1); columns.put(Data.SYNC2, Data.SYNC2)704 columns.put(Data.SYNC2, Data.SYNC2); columns.put(Data.SYNC3, Data.SYNC3)705 columns.put(Data.SYNC3, Data.SYNC3); columns.put(Data.SYNC4, Data.SYNC4)706 columns.put(Data.SYNC4, Data.SYNC4); columns.put(RawContacts.Entity.DATA_ID, RawContacts.Entity.DATA_ID)707 columns.put(RawContacts.Entity.DATA_ID, RawContacts.Entity.DATA_ID); columns.put(Data.STARRED, Data.STARRED)708 columns.put(Data.STARRED, Data.STARRED); columns.put(Data.DATA_VERSION, Data.DATA_VERSION)709 columns.put(Data.DATA_VERSION, Data.DATA_VERSION); columns.put(Data.IS_PRIMARY, Data.IS_PRIMARY)710 columns.put(Data.IS_PRIMARY, Data.IS_PRIMARY); columns.put(Data.IS_SUPER_PRIMARY, Data.IS_SUPER_PRIMARY)711 columns.put(Data.IS_SUPER_PRIMARY, Data.IS_SUPER_PRIMARY); columns.put(GroupMembership.GROUP_SOURCE_ID, GroupMembership.GROUP_SOURCE_ID)712 columns.put(GroupMembership.GROUP_SOURCE_ID, GroupMembership.GROUP_SOURCE_ID); 713 sRawContactsEntityProjectionMap = columns; 714 715 // Handle projections for Contacts-level statuses addProjection(sDataProjectionMap, Contacts.CONTACT_PRESENCE, Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.PRESENCE)716 addProjection(sDataProjectionMap, Contacts.CONTACT_PRESENCE, 717 Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.PRESENCE); addProjection(sContactsProjectionMap, Contacts.CONTACT_CHAT_CAPABILITY, Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY)718 addProjection(sContactsProjectionMap, Contacts.CONTACT_CHAT_CAPABILITY, 719 Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY); addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS, ContactsStatusUpdatesColumns.CONCRETE_STATUS)720 addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS, 721 ContactsStatusUpdatesColumns.CONCRETE_STATUS); addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS_TIMESTAMP, ContactsStatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP)722 addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS_TIMESTAMP, 723 ContactsStatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP); addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS_RES_PACKAGE, ContactsStatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE)724 addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS_RES_PACKAGE, 725 ContactsStatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE); addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS_LABEL, ContactsStatusUpdatesColumns.CONCRETE_STATUS_LABEL)726 addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS_LABEL, 727 ContactsStatusUpdatesColumns.CONCRETE_STATUS_LABEL); addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS_ICON, ContactsStatusUpdatesColumns.CONCRETE_STATUS_ICON)728 addProjection(sDataProjectionMap, Contacts.CONTACT_STATUS_ICON, 729 ContactsStatusUpdatesColumns.CONCRETE_STATUS_ICON); 730 731 // Handle projections for Data-level statuses addProjection(sDataProjectionMap, Data.PRESENCE, Tables.PRESENCE + "." + StatusUpdates.PRESENCE)732 addProjection(sDataProjectionMap, Data.PRESENCE, 733 Tables.PRESENCE + "." + StatusUpdates.PRESENCE); addProjection(sDataProjectionMap, Data.CONTACT_CHAT_CAPABILITY, Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY)734 addProjection(sDataProjectionMap, Data.CONTACT_CHAT_CAPABILITY, 735 Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY); addProjection(sDataProjectionMap, Data.STATUS, StatusUpdatesColumns.CONCRETE_STATUS)736 addProjection(sDataProjectionMap, Data.STATUS, 737 StatusUpdatesColumns.CONCRETE_STATUS); addProjection(sDataProjectionMap, Data.STATUS_TIMESTAMP, StatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP)738 addProjection(sDataProjectionMap, Data.STATUS_TIMESTAMP, 739 StatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP); addProjection(sDataProjectionMap, Data.STATUS_RES_PACKAGE, StatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE)740 addProjection(sDataProjectionMap, Data.STATUS_RES_PACKAGE, 741 StatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE); addProjection(sDataProjectionMap, Data.STATUS_LABEL, StatusUpdatesColumns.CONCRETE_STATUS_LABEL)742 addProjection(sDataProjectionMap, Data.STATUS_LABEL, 743 StatusUpdatesColumns.CONCRETE_STATUS_LABEL); addProjection(sDataProjectionMap, Data.STATUS_ICON, StatusUpdatesColumns.CONCRETE_STATUS_ICON)744 addProjection(sDataProjectionMap, Data.STATUS_ICON, 745 StatusUpdatesColumns.CONCRETE_STATUS_ICON); 746 747 // Projection map for data grouped by contact (not raw contact) and some data field(s) 748 sDistinctDataProjectionMap = new HashMap<String, String>(); sDistinctDataProjectionMap.put(Data._ID, "MIN(" + Data._ID + ") AS " + Data._ID)749 sDistinctDataProjectionMap.put(Data._ID, 750 "MIN(" + Data._ID + ") AS " + Data._ID); sDistinctDataProjectionMap.put(Data.DATA_VERSION, Data.DATA_VERSION)751 sDistinctDataProjectionMap.put(Data.DATA_VERSION, Data.DATA_VERSION); sDistinctDataProjectionMap.put(Data.IS_PRIMARY, Data.IS_PRIMARY)752 sDistinctDataProjectionMap.put(Data.IS_PRIMARY, Data.IS_PRIMARY); sDistinctDataProjectionMap.put(Data.IS_SUPER_PRIMARY, Data.IS_SUPER_PRIMARY)753 sDistinctDataProjectionMap.put(Data.IS_SUPER_PRIMARY, Data.IS_SUPER_PRIMARY); sDistinctDataProjectionMap.put(Data.RES_PACKAGE, Data.RES_PACKAGE)754 sDistinctDataProjectionMap.put(Data.RES_PACKAGE, Data.RES_PACKAGE); sDistinctDataProjectionMap.put(Data.MIMETYPE, Data.MIMETYPE)755 sDistinctDataProjectionMap.put(Data.MIMETYPE, Data.MIMETYPE); sDistinctDataProjectionMap.put(Data.DATA1, Data.DATA1)756 sDistinctDataProjectionMap.put(Data.DATA1, Data.DATA1); sDistinctDataProjectionMap.put(Data.DATA2, Data.DATA2)757 sDistinctDataProjectionMap.put(Data.DATA2, Data.DATA2); sDistinctDataProjectionMap.put(Data.DATA3, Data.DATA3)758 sDistinctDataProjectionMap.put(Data.DATA3, Data.DATA3); sDistinctDataProjectionMap.put(Data.DATA4, Data.DATA4)759 sDistinctDataProjectionMap.put(Data.DATA4, Data.DATA4); sDistinctDataProjectionMap.put(Data.DATA5, Data.DATA5)760 sDistinctDataProjectionMap.put(Data.DATA5, Data.DATA5); sDistinctDataProjectionMap.put(Data.DATA6, Data.DATA6)761 sDistinctDataProjectionMap.put(Data.DATA6, Data.DATA6); sDistinctDataProjectionMap.put(Data.DATA7, Data.DATA7)762 sDistinctDataProjectionMap.put(Data.DATA7, Data.DATA7); sDistinctDataProjectionMap.put(Data.DATA8, Data.DATA8)763 sDistinctDataProjectionMap.put(Data.DATA8, Data.DATA8); sDistinctDataProjectionMap.put(Data.DATA9, Data.DATA9)764 sDistinctDataProjectionMap.put(Data.DATA9, Data.DATA9); sDistinctDataProjectionMap.put(Data.DATA10, Data.DATA10)765 sDistinctDataProjectionMap.put(Data.DATA10, Data.DATA10); sDistinctDataProjectionMap.put(Data.DATA11, Data.DATA11)766 sDistinctDataProjectionMap.put(Data.DATA11, Data.DATA11); sDistinctDataProjectionMap.put(Data.DATA12, Data.DATA12)767 sDistinctDataProjectionMap.put(Data.DATA12, Data.DATA12); sDistinctDataProjectionMap.put(Data.DATA13, Data.DATA13)768 sDistinctDataProjectionMap.put(Data.DATA13, Data.DATA13); sDistinctDataProjectionMap.put(Data.DATA14, Data.DATA14)769 sDistinctDataProjectionMap.put(Data.DATA14, Data.DATA14); sDistinctDataProjectionMap.put(Data.DATA15, Data.DATA15)770 sDistinctDataProjectionMap.put(Data.DATA15, Data.DATA15); sDistinctDataProjectionMap.put(Data.SYNC1, Data.SYNC1)771 sDistinctDataProjectionMap.put(Data.SYNC1, Data.SYNC1); sDistinctDataProjectionMap.put(Data.SYNC2, Data.SYNC2)772 sDistinctDataProjectionMap.put(Data.SYNC2, Data.SYNC2); sDistinctDataProjectionMap.put(Data.SYNC3, Data.SYNC3)773 sDistinctDataProjectionMap.put(Data.SYNC3, Data.SYNC3); sDistinctDataProjectionMap.put(Data.SYNC4, Data.SYNC4)774 sDistinctDataProjectionMap.put(Data.SYNC4, Data.SYNC4); sDistinctDataProjectionMap.put(RawContacts.CONTACT_ID, RawContacts.CONTACT_ID)775 sDistinctDataProjectionMap.put(RawContacts.CONTACT_ID, RawContacts.CONTACT_ID); sDistinctDataProjectionMap.put(Contacts.LOOKUP_KEY, Contacts.LOOKUP_KEY)776 sDistinctDataProjectionMap.put(Contacts.LOOKUP_KEY, Contacts.LOOKUP_KEY); sDistinctDataProjectionMap.put(Contacts.DISPLAY_NAME, Contacts.DISPLAY_NAME)777 sDistinctDataProjectionMap.put(Contacts.DISPLAY_NAME, Contacts.DISPLAY_NAME); sDistinctDataProjectionMap.put(Contacts.DISPLAY_NAME_ALTERNATIVE, Contacts.DISPLAY_NAME_ALTERNATIVE)778 sDistinctDataProjectionMap.put(Contacts.DISPLAY_NAME_ALTERNATIVE, 779 Contacts.DISPLAY_NAME_ALTERNATIVE); sDistinctDataProjectionMap.put(Contacts.DISPLAY_NAME_SOURCE, Contacts.DISPLAY_NAME_SOURCE)780 sDistinctDataProjectionMap.put(Contacts.DISPLAY_NAME_SOURCE, Contacts.DISPLAY_NAME_SOURCE); sDistinctDataProjectionMap.put(Contacts.PHONETIC_NAME, Contacts.PHONETIC_NAME)781 sDistinctDataProjectionMap.put(Contacts.PHONETIC_NAME, Contacts.PHONETIC_NAME); sDistinctDataProjectionMap.put(Contacts.PHONETIC_NAME_STYLE, Contacts.PHONETIC_NAME_STYLE)782 sDistinctDataProjectionMap.put(Contacts.PHONETIC_NAME_STYLE, Contacts.PHONETIC_NAME_STYLE); sDistinctDataProjectionMap.put(Contacts.SORT_KEY_PRIMARY, Contacts.SORT_KEY_PRIMARY)783 sDistinctDataProjectionMap.put(Contacts.SORT_KEY_PRIMARY, Contacts.SORT_KEY_PRIMARY); sDistinctDataProjectionMap.put(Contacts.SORT_KEY_ALTERNATIVE, Contacts.SORT_KEY_ALTERNATIVE)784 sDistinctDataProjectionMap.put(Contacts.SORT_KEY_ALTERNATIVE, 785 Contacts.SORT_KEY_ALTERNATIVE); sDistinctDataProjectionMap.put(Contacts.CUSTOM_RINGTONE, Contacts.CUSTOM_RINGTONE)786 sDistinctDataProjectionMap.put(Contacts.CUSTOM_RINGTONE, Contacts.CUSTOM_RINGTONE); sDistinctDataProjectionMap.put(Contacts.SEND_TO_VOICEMAIL, Contacts.SEND_TO_VOICEMAIL)787 sDistinctDataProjectionMap.put(Contacts.SEND_TO_VOICEMAIL, Contacts.SEND_TO_VOICEMAIL); sDistinctDataProjectionMap.put(Contacts.LAST_TIME_CONTACTED, Contacts.LAST_TIME_CONTACTED)788 sDistinctDataProjectionMap.put(Contacts.LAST_TIME_CONTACTED, Contacts.LAST_TIME_CONTACTED); sDistinctDataProjectionMap.put(Contacts.TIMES_CONTACTED, Contacts.TIMES_CONTACTED)789 sDistinctDataProjectionMap.put(Contacts.TIMES_CONTACTED, Contacts.TIMES_CONTACTED); sDistinctDataProjectionMap.put(Contacts.STARRED, Contacts.STARRED)790 sDistinctDataProjectionMap.put(Contacts.STARRED, Contacts.STARRED); sDistinctDataProjectionMap.put(Contacts.PHOTO_ID, Contacts.PHOTO_ID)791 sDistinctDataProjectionMap.put(Contacts.PHOTO_ID, Contacts.PHOTO_ID); sDistinctDataProjectionMap.put(Contacts.IN_VISIBLE_GROUP, Contacts.IN_VISIBLE_GROUP)792 sDistinctDataProjectionMap.put(Contacts.IN_VISIBLE_GROUP, Contacts.IN_VISIBLE_GROUP); sDistinctDataProjectionMap.put(GroupMembership.GROUP_SOURCE_ID, GroupMembership.GROUP_SOURCE_ID)793 sDistinctDataProjectionMap.put(GroupMembership.GROUP_SOURCE_ID, 794 GroupMembership.GROUP_SOURCE_ID); 795 796 // Handle projections for Contacts-level statuses addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_PRESENCE, Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.PRESENCE)797 addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_PRESENCE, 798 Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.PRESENCE); addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_CHAT_CAPABILITY, Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY)799 addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_CHAT_CAPABILITY, 800 Tables.AGGREGATED_PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY); addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS, ContactsStatusUpdatesColumns.CONCRETE_STATUS)801 addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS, 802 ContactsStatusUpdatesColumns.CONCRETE_STATUS); addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS_TIMESTAMP, ContactsStatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP)803 addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS_TIMESTAMP, 804 ContactsStatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP); addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS_RES_PACKAGE, ContactsStatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE)805 addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS_RES_PACKAGE, 806 ContactsStatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE); addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS_LABEL, ContactsStatusUpdatesColumns.CONCRETE_STATUS_LABEL)807 addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS_LABEL, 808 ContactsStatusUpdatesColumns.CONCRETE_STATUS_LABEL); addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS_ICON, ContactsStatusUpdatesColumns.CONCRETE_STATUS_ICON)809 addProjection(sDistinctDataProjectionMap, Contacts.CONTACT_STATUS_ICON, 810 ContactsStatusUpdatesColumns.CONCRETE_STATUS_ICON); 811 812 // Handle projections for Data-level statuses addProjection(sDistinctDataProjectionMap, Data.PRESENCE, Tables.PRESENCE + "." + StatusUpdates.PRESENCE)813 addProjection(sDistinctDataProjectionMap, Data.PRESENCE, 814 Tables.PRESENCE + "." + StatusUpdates.PRESENCE); addProjection(sDistinctDataProjectionMap, Data.CHAT_CAPABILITY, Tables.PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY)815 addProjection(sDistinctDataProjectionMap, Data.CHAT_CAPABILITY, 816 Tables.PRESENCE + "." + StatusUpdates.CHAT_CAPABILITY); addProjection(sDistinctDataProjectionMap, Data.STATUS, StatusUpdatesColumns.CONCRETE_STATUS)817 addProjection(sDistinctDataProjectionMap, Data.STATUS, 818 StatusUpdatesColumns.CONCRETE_STATUS); addProjection(sDistinctDataProjectionMap, Data.STATUS_TIMESTAMP, StatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP)819 addProjection(sDistinctDataProjectionMap, Data.STATUS_TIMESTAMP, 820 StatusUpdatesColumns.CONCRETE_STATUS_TIMESTAMP); addProjection(sDistinctDataProjectionMap, Data.STATUS_RES_PACKAGE, StatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE)821 addProjection(sDistinctDataProjectionMap, Data.STATUS_RES_PACKAGE, 822 StatusUpdatesColumns.CONCRETE_STATUS_RES_PACKAGE); addProjection(sDistinctDataProjectionMap, Data.STATUS_LABEL, StatusUpdatesColumns.CONCRETE_STATUS_LABEL)823 addProjection(sDistinctDataProjectionMap, Data.STATUS_LABEL, 824 StatusUpdatesColumns.CONCRETE_STATUS_LABEL); addProjection(sDistinctDataProjectionMap, Data.STATUS_ICON, StatusUpdatesColumns.CONCRETE_STATUS_ICON)825 addProjection(sDistinctDataProjectionMap, Data.STATUS_ICON, 826 StatusUpdatesColumns.CONCRETE_STATUS_ICON); 827 828 sPhoneLookupProjectionMap = new HashMap<String, String>(); sPhoneLookupProjectionMap.put(PhoneLookup._ID, "contacts_view." + Contacts._ID + " AS " + PhoneLookup._ID)829 sPhoneLookupProjectionMap.put(PhoneLookup._ID, 830 "contacts_view." + Contacts._ID 831 + " AS " + PhoneLookup._ID); sPhoneLookupProjectionMap.put(PhoneLookup.LOOKUP_KEY, "contacts_view." + Contacts.LOOKUP_KEY + " AS " + PhoneLookup.LOOKUP_KEY)832 sPhoneLookupProjectionMap.put(PhoneLookup.LOOKUP_KEY, 833 "contacts_view." + Contacts.LOOKUP_KEY 834 + " AS " + PhoneLookup.LOOKUP_KEY); sPhoneLookupProjectionMap.put(PhoneLookup.DISPLAY_NAME, "contacts_view." + Contacts.DISPLAY_NAME + " AS " + PhoneLookup.DISPLAY_NAME)835 sPhoneLookupProjectionMap.put(PhoneLookup.DISPLAY_NAME, 836 "contacts_view." + Contacts.DISPLAY_NAME 837 + " AS " + PhoneLookup.DISPLAY_NAME); sPhoneLookupProjectionMap.put(PhoneLookup.LAST_TIME_CONTACTED, "contacts_view." + Contacts.LAST_TIME_CONTACTED + " AS " + PhoneLookup.LAST_TIME_CONTACTED)838