Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit b2c8e1c6 authored by Treehugger Robot's avatar Treehugger Robot Committed by Gerrit Code Review
Browse files

Merge "Look up contacts in the local enterprise directory in the new call log."

parents 95eb620c 3506a5f7
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -96,7 +96,7 @@ public final class RealtimeRowProcessor {
   */
  @MainThread
  ListenableFuture<CoalescedRow> applyRealtimeProcessing(final CoalescedRow row) {
    // Cp2LocalPhoneLookup can not always efficiently process all rows.
    // Cp2DefaultDirectoryPhoneLookup can not always efficiently process all rows.
    if (!row.numberAttributes().getIsCp2InfoIncomplete()) {
      return Futures.immediateFuture(row);
    }
+1 −1
Original line number Diff line number Diff line
@@ -56,6 +56,6 @@ public final class NumberAttributesConverter {
        .setIsBlocked(phoneLookupInfoConsolidator.isBlocked())
        .setIsSpam(phoneLookupInfoConsolidator.isSpam())
        .setCanReportAsInvalidNumber(phoneLookupInfoConsolidator.canReportAsInvalidNumber())
        .setIsCp2InfoIncomplete(phoneLookupInfoConsolidator.isCp2LocalInfoIncomplete());
        .setIsCp2InfoIncomplete(phoneLookupInfoConsolidator.isDefaultCp2InfoIncomplete());
  }
}
+6 −6
Original line number Diff line number Diff line
@@ -18,8 +18,8 @@ package com.android.dialer.phonelookup;

import com.android.dialer.phonelookup.blockednumber.DialerBlockedNumberPhoneLookup;
import com.android.dialer.phonelookup.blockednumber.SystemBlockedNumberPhoneLookup;
import com.android.dialer.phonelookup.cp2.Cp2LocalPhoneLookup;
import com.android.dialer.phonelookup.cp2.Cp2RemotePhoneLookup;
import com.android.dialer.phonelookup.cp2.Cp2DefaultDirectoryPhoneLookup;
import com.android.dialer.phonelookup.cp2.Cp2ExtendedDirectoryPhoneLookup;
import com.android.dialer.phonelookup.spam.SpamPhoneLookup;
import com.google.common.collect.ImmutableList;
import dagger.Module;
@@ -32,14 +32,14 @@ public abstract class PhoneLookupModule {
  @Provides
  @SuppressWarnings({"unchecked", "rawtype"})
  static ImmutableList<PhoneLookup> providePhoneLookupList(
      Cp2LocalPhoneLookup cp2LocalPhoneLookup,
      Cp2RemotePhoneLookup cp2RemotePhoneLookup,
      Cp2DefaultDirectoryPhoneLookup cp2DefaultDirectoryPhoneLookup,
      Cp2ExtendedDirectoryPhoneLookup cp2ExtendedDirectoryPhoneLookup,
      DialerBlockedNumberPhoneLookup dialerBlockedNumberPhoneLookup,
      SystemBlockedNumberPhoneLookup systemBlockedNumberPhoneLookup,
      SpamPhoneLookup spamPhoneLookup) {
    return ImmutableList.of(
        cp2LocalPhoneLookup,
        cp2RemotePhoneLookup,
        cp2DefaultDirectoryPhoneLookup,
        cp2ExtendedDirectoryPhoneLookup,
        dialerBlockedNumberPhoneLookup,
        systemBlockedNumberPhoneLookup,
        spamPhoneLookup);
+72 −63
Original line number Diff line number Diff line
@@ -40,11 +40,16 @@ public final class PhoneLookupInfoConsolidator {

  /** Integers representing {@link PhoneLookup} implementations that can provide a contact's name */
  @Retention(RetentionPolicy.SOURCE)
  @IntDef({NameSource.NONE, NameSource.CP2_LOCAL, NameSource.CP2_REMOTE, NameSource.PEOPLE_API})
  @IntDef({
    NameSource.NONE,
    NameSource.CP2_DEFAULT_DIRECTORY,
    NameSource.CP2_EXTENDED_DIRECTORY,
    NameSource.PEOPLE_API
  })
  @interface NameSource {
    int NONE = 0; // used when none of the other sources can provide the name
    int CP2_LOCAL = 1;
    int CP2_REMOTE = 2;
    int CP2_DEFAULT_DIRECTORY = 1;
    int CP2_EXTENDED_DIRECTORY = 2;
    int PEOPLE_API = 3;
  }

@@ -53,31 +58,35 @@ public final class PhoneLookupInfoConsolidator {
   *
   * <p>Each source is one of the values in NameSource, as defined above.
   *
   * <p>Sources are sorted in the order of priority. For example, if source CP2_LOCAL can provide
   * the name, we will use that name in the UI and ignore all the other sources. If source CP2_LOCAL
   * can't provide the name, source CP2_REMOTE will be consulted.
   * <p>Sources are sorted in the order of priority. For example, if source CP2_DEFAULT_DIRECTORY
   * can provide the name, we will use that name in the UI and ignore all the other sources. If
   * source CP2_DEFAULT_DIRECTORY can't provide the name, source CP2_EXTENDED_DIRECTORY will be
   * consulted.
   *
   * <p>The reason for defining a name source is to avoid mixing info from different sub-messages in
   * PhoneLookupInfo proto when we are supposed to stick with only one sub-message. For example, if
   * a PhoneLookupInfo proto has both cp2_local_info and cp2_remote_info but only cp2_remote_info
   * has a photo URI, PhoneLookupInfoConsolidator should provide an empty photo URI as CP2_LOCAL has
   * higher priority and we should not use cp2_remote_info's photo URI to display the contact's
   * photo.
   * a PhoneLookupInfo proto has both default_cp2_info and extended_cp2_info but only
   * extended_cp2_info has a photo URI, PhoneLookupInfoConsolidator should provide an empty photo
   * URI as CP2_DEFAULT_DIRECTORY has higher priority and we should not use extended_cp2_info's
   * photo URI to display the contact's photo.
   */
  private static final ImmutableList<Integer> NAME_SOURCES_IN_PRIORITY_ORDER =
      ImmutableList.of(NameSource.CP2_LOCAL, NameSource.CP2_REMOTE, NameSource.PEOPLE_API);
      ImmutableList.of(
          NameSource.CP2_DEFAULT_DIRECTORY,
          NameSource.CP2_EXTENDED_DIRECTORY,
          NameSource.PEOPLE_API);

  private final @NameSource int nameSource;
  private final PhoneLookupInfo phoneLookupInfo;

  @Nullable private final Cp2ContactInfo firstCp2LocalContact;
  @Nullable private final Cp2ContactInfo firstCp2RemoteContact;
  @Nullable private final Cp2ContactInfo firstDefaultCp2Contact;
  @Nullable private final Cp2ContactInfo firstExtendedCp2Contact;

  public PhoneLookupInfoConsolidator(PhoneLookupInfo phoneLookupInfo) {
    this.phoneLookupInfo = phoneLookupInfo;

    this.firstCp2LocalContact = getFirstLocalContact();
    this.firstCp2RemoteContact = getFirstRemoteContact();
    this.firstDefaultCp2Contact = getFirstContactInDefaultDirectory();
    this.firstExtendedCp2Contact = getFirstContactInExtendedDirectories();
    this.nameSource = selectNameSource();
  }

@@ -92,10 +101,10 @@ public final class PhoneLookupInfoConsolidator {
   */
  public String getName() {
    switch (nameSource) {
      case NameSource.CP2_LOCAL:
        return Assert.isNotNull(firstCp2LocalContact).getName();
      case NameSource.CP2_REMOTE:
        return Assert.isNotNull(firstCp2RemoteContact).getName();
      case NameSource.CP2_DEFAULT_DIRECTORY:
        return Assert.isNotNull(firstDefaultCp2Contact).getName();
      case NameSource.CP2_EXTENDED_DIRECTORY:
        return Assert.isNotNull(firstExtendedCp2Contact).getName();
      case NameSource.PEOPLE_API:
        return phoneLookupInfo.getPeopleApiInfo().getDisplayName();
      case NameSource.NONE:
@@ -115,10 +124,10 @@ public final class PhoneLookupInfoConsolidator {
   */
  public String getPhotoThumbnailUri() {
    switch (nameSource) {
      case NameSource.CP2_LOCAL:
        return Assert.isNotNull(firstCp2LocalContact).getPhotoThumbnailUri();
      case NameSource.CP2_REMOTE:
        return Assert.isNotNull(firstCp2RemoteContact).getPhotoThumbnailUri();
      case NameSource.CP2_DEFAULT_DIRECTORY:
        return Assert.isNotNull(firstDefaultCp2Contact).getPhotoThumbnailUri();
      case NameSource.CP2_EXTENDED_DIRECTORY:
        return Assert.isNotNull(firstExtendedCp2Contact).getPhotoThumbnailUri();
      case NameSource.PEOPLE_API:
      case NameSource.NONE:
        return "";
@@ -137,10 +146,10 @@ public final class PhoneLookupInfoConsolidator {
   */
  public String getPhotoUri() {
    switch (nameSource) {
      case NameSource.CP2_LOCAL:
        return Assert.isNotNull(firstCp2LocalContact).getPhotoUri();
      case NameSource.CP2_REMOTE:
        return Assert.isNotNull(firstCp2RemoteContact).getPhotoUri();
      case NameSource.CP2_DEFAULT_DIRECTORY:
        return Assert.isNotNull(firstDefaultCp2Contact).getPhotoUri();
      case NameSource.CP2_EXTENDED_DIRECTORY:
        return Assert.isNotNull(firstExtendedCp2Contact).getPhotoUri();
      case NameSource.PEOPLE_API:
      case NameSource.NONE:
        return "";
@@ -156,10 +165,10 @@ public final class PhoneLookupInfoConsolidator {
   */
  public long getPhotoId() {
    switch (nameSource) {
      case NameSource.CP2_LOCAL:
        return Math.max(Assert.isNotNull(firstCp2LocalContact).getPhotoId(), 0);
      case NameSource.CP2_REMOTE:
        return Math.max(Assert.isNotNull(firstCp2RemoteContact).getPhotoId(), 0);
      case NameSource.CP2_DEFAULT_DIRECTORY:
        return Math.max(Assert.isNotNull(firstDefaultCp2Contact).getPhotoId(), 0);
      case NameSource.CP2_EXTENDED_DIRECTORY:
        return Math.max(Assert.isNotNull(firstExtendedCp2Contact).getPhotoId(), 0);
      case NameSource.PEOPLE_API:
      case NameSource.NONE:
        return 0;
@@ -176,10 +185,10 @@ public final class PhoneLookupInfoConsolidator {
   */
  public String getLookupUri() {
    switch (nameSource) {
      case NameSource.CP2_LOCAL:
        return Assert.isNotNull(firstCp2LocalContact).getLookupUri();
      case NameSource.CP2_REMOTE:
        return Assert.isNotNull(firstCp2RemoteContact).getLookupUri();
      case NameSource.CP2_DEFAULT_DIRECTORY:
        return Assert.isNotNull(firstDefaultCp2Contact).getLookupUri();
      case NameSource.CP2_EXTENDED_DIRECTORY:
        return Assert.isNotNull(firstExtendedCp2Contact).getLookupUri();
      case NameSource.PEOPLE_API:
        return Assert.isNotNull(phoneLookupInfo.getPeopleApiInfo().getLookupUri());
      case NameSource.NONE:
@@ -200,10 +209,10 @@ public final class PhoneLookupInfoConsolidator {
   */
  public String getNumberLabel() {
    switch (nameSource) {
      case NameSource.CP2_LOCAL:
        return Assert.isNotNull(firstCp2LocalContact).getLabel();
      case NameSource.CP2_REMOTE:
        return Assert.isNotNull(firstCp2RemoteContact).getLabel();
      case NameSource.CP2_DEFAULT_DIRECTORY:
        return Assert.isNotNull(firstDefaultCp2Contact).getLabel();
      case NameSource.CP2_EXTENDED_DIRECTORY:
        return Assert.isNotNull(firstExtendedCp2Contact).getLabel();
      case NameSource.PEOPLE_API:
      case NameSource.NONE:
        return "";
@@ -259,11 +268,11 @@ public final class PhoneLookupInfoConsolidator {
  }

  /**
   * Returns true if the {@link PhoneLookupInfo} passed to the constructor has incomplete CP2 local
   * info.
   * Returns true if the {@link PhoneLookupInfo} passed to the constructor has incomplete default
   * CP2 info (info from the default directory).
   */
  public boolean isCp2LocalInfoIncomplete() {
    return phoneLookupInfo.getCp2LocalInfo().getIsIncomplete();
  public boolean isDefaultCp2InfoIncomplete() {
    return phoneLookupInfo.getDefaultCp2Info().getIsIncomplete();
  }

  /**
@@ -275,8 +284,8 @@ public final class PhoneLookupInfoConsolidator {
   */
  public boolean canReportAsInvalidNumber() {
    switch (nameSource) {
      case NameSource.CP2_LOCAL:
      case NameSource.CP2_REMOTE:
      case NameSource.CP2_DEFAULT_DIRECTORY:
      case NameSource.CP2_EXTENDED_DIRECTORY:
        return false;
      case NameSource.PEOPLE_API:
        PeopleApiInfo peopleApiInfo = phoneLookupInfo.getPeopleApiInfo();
@@ -291,26 +300,26 @@ public final class PhoneLookupInfoConsolidator {
  }

  /**
   * Arbitrarily select the first local CP2 contact. In the future, it may make sense to display
   * contact information from all contacts with the same number (for example show the name as "Mom,
   * Dad" or show a synthesized photo containing photos of both "Mom" and "Dad").
   * Arbitrarily select the first CP2 contact in the default directory. In the future, it may make
   * sense to display contact information from all contacts with the same number (for example show
   * the name as "Mom, Dad" or show a synthesized photo containing photos of both "Mom" and "Dad").
   */
  @Nullable
  private Cp2ContactInfo getFirstLocalContact() {
    return phoneLookupInfo.getCp2LocalInfo().getCp2ContactInfoCount() > 0
        ? phoneLookupInfo.getCp2LocalInfo().getCp2ContactInfo(0)
  private Cp2ContactInfo getFirstContactInDefaultDirectory() {
    return phoneLookupInfo.getDefaultCp2Info().getCp2ContactInfoCount() > 0
        ? phoneLookupInfo.getDefaultCp2Info().getCp2ContactInfo(0)
        : null;
  }

  /**
   * Arbitrarily select the first remote CP2 contact. In the future, it may make sense to display
   * contact information from all contacts with the same number (for example show the name as "Mom,
   * Dad" or show a synthesized photo containing photos of both "Mom" and "Dad").
   * Arbitrarily select the first CP2 contact in extended directories. In the future, it may make
   * sense to display contact information from all contacts with the same number (for example show
   * the name as "Mom, Dad" or show a synthesized photo containing photos of both "Mom" and "Dad").
   */
  @Nullable
  private Cp2ContactInfo getFirstRemoteContact() {
    return phoneLookupInfo.getCp2RemoteInfo().getCp2ContactInfoCount() > 0
        ? phoneLookupInfo.getCp2RemoteInfo().getCp2ContactInfo(0)
  private Cp2ContactInfo getFirstContactInExtendedDirectories() {
    return phoneLookupInfo.getExtendedCp2Info().getCp2ContactInfoCount() > 0
        ? phoneLookupInfo.getExtendedCp2Info().getCp2ContactInfo(0)
        : null;
  }

@@ -318,14 +327,14 @@ public final class PhoneLookupInfoConsolidator {
  private @NameSource int selectNameSource() {
    for (int nameSource : NAME_SOURCES_IN_PRIORITY_ORDER) {
      switch (nameSource) {
        case NameSource.CP2_LOCAL:
          if (firstCp2LocalContact != null && !firstCp2LocalContact.getName().isEmpty()) {
            return NameSource.CP2_LOCAL;
        case NameSource.CP2_DEFAULT_DIRECTORY:
          if (firstDefaultCp2Contact != null && !firstDefaultCp2Contact.getName().isEmpty()) {
            return NameSource.CP2_DEFAULT_DIRECTORY;
          }
          break;
        case NameSource.CP2_REMOTE:
          if (firstCp2RemoteContact != null && !firstCp2RemoteContact.getName().isEmpty()) {
            return NameSource.CP2_REMOTE;
        case NameSource.CP2_EXTENDED_DIRECTORY:
          if (firstExtendedCp2Contact != null && !firstExtendedCp2Contact.getName().isEmpty()) {
            return NameSource.CP2_EXTENDED_DIRECTORY;
          }
          break;
        case NameSource.PEOPLE_API:
+25 −20
Original line number Diff line number Diff line
@@ -58,11 +58,11 @@ import java.util.Set;
import java.util.concurrent.Callable;
import javax.inject.Inject;

/** PhoneLookup implementation for local contacts. */
public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
/** PhoneLookup implementation for contacts in the default directory. */
public final class Cp2DefaultDirectoryPhoneLookup implements PhoneLookup<Cp2Info> {

  private static final String PREF_LAST_TIMESTAMP_PROCESSED =
      "cp2LocalPhoneLookupLastTimestampProcessed";
      "cp2DefaultDirectoryPhoneLookupLastTimestampProcessed";

  // We cannot efficiently process invalid numbers because batch queries cannot be constructed which
  // accomplish the necessary loose matching. We'll attempt to process a limited number of them,
@@ -77,7 +77,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
  @Nullable private Long currentLastTimestampProcessed;

  @Inject
  Cp2LocalPhoneLookup(
  Cp2DefaultDirectoryPhoneLookup(
      @ApplicationContext Context appContext,
      @Unencrypted SharedPreferences sharedPreferences,
      @BackgroundExecutor ListeningExecutorService backgroundExecutorService,
@@ -121,7 +121,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
                Iterables.getOnlyElement(partitionedNumbers.invalidNumbers()));
      }
      if (cursor == null) {
        LogUtil.w("Cp2LocalPhoneLookup.lookupInternal", "null cursor");
        LogUtil.w("Cp2DefaultDirectoryPhoneLookup.lookupInternal", "null cursor");
        return Cp2Info.getDefaultInstance();
      }
      while (cursor.moveToNext()) {
@@ -144,7 +144,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
      // check, simply return true. The expectation is that this should rarely be the case as the
      // vast majority of numbers in call logs should be valid.
      LogUtil.v(
          "Cp2LocalPhoneLookup.isDirty",
          "Cp2DefaultDirectoryPhoneLookup.isDirty",
          "returning true because too many invalid numbers (%d)",
          partitionedNumbers.invalidNumbers().size());
      return Futures.immediateFuture(true);
@@ -164,7 +164,8 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
              anyContactsDeleted -> {
                if (anyContactsDeleted) {
                  LogUtil.v(
                      "Cp2LocalPhoneLookup.isDirty", "returning true because contacts deleted");
                      "Cp2DefaultDirectoryPhoneLookup.isDirty",
                      "returning true because contacts deleted");
                  return Futures.immediateFuture(true);
                }
                // Hopefully the most common case is there are no contacts updated; we can detect
@@ -176,7 +177,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
                    noContactsModifiedSince -> {
                      if (noContactsModifiedSince) {
                        LogUtil.v(
                            "Cp2LocalPhoneLookup.isDirty",
                            "Cp2DefaultDirectoryPhoneLookup.isDirty",
                            "returning false because no contacts modified since last run");
                        return Futures.immediateFuture(false);
                      }
@@ -194,7 +195,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
                          contactsUpdated -> {
                            if (contactsUpdated) {
                              LogUtil.v(
                                  "Cp2LocalPhoneLookup.isDirty",
                                  "Cp2DefaultDirectoryPhoneLookup.isDirty",
                                  "returning true because a previously called contact was updated");
                              return Futures.immediateFuture(true);
                            }
@@ -267,7 +268,9 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
                      null)) {

            if (cursor == null) {
              LogUtil.w("Cp2LocalPhoneLookup.queryPhoneLookupHistoryForContactIds", "null cursor");
              LogUtil.w(
                  "Cp2DefaultDirectoryPhoneLookup.queryPhoneLookupHistoryForContactIds",
                  "null cursor");
              return contactIds;
            }

@@ -283,7 +286,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
                  throw new IllegalStateException(e);
                }
                for (Cp2ContactInfo info :
                    phoneLookupInfo.getCp2LocalInfo().getCp2ContactInfoList()) {
                    phoneLookupInfo.getDefaultCp2Info().getCp2ContactInfoList()) {
                  contactIds.add(info.getContactId());
                }
              } while (cursor.moveToNext());
@@ -305,7 +308,8 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
              queryPhoneTableBasedOnE164(new String[] {Phone.CONTACT_ID}, validE164Numbers)) {
            if (cursor == null) {
              LogUtil.w(
                  "Cp2LocalPhoneLookup.queryPhoneTableForContactIdsBasedOnE164", "null cursor");
                  "Cp2DefaultDirectoryPhoneLookup.queryPhoneTableForContactIdsBasedOnE164",
                  "null cursor");
              return contactIds;
            }
            while (cursor.moveToNext()) {
@@ -328,7 +332,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
              queryPhoneLookup(new String[] {ContactsContract.PhoneLookup.CONTACT_ID}, rawNumber)) {
            if (cursor == null) {
              LogUtil.w(
                  "Cp2LocalPhoneLookup.queryPhoneLookupTableForContactIdsBasedOnRawNumber",
                  "Cp2DefaultDirectoryPhoneLookup.queryPhoneLookupTableForContactIdsBasedOnRawNumber",
                  "null cursor");
              return contactIds;
            }
@@ -391,7 +395,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
                      new String[] {Long.toString(lastModified)},
                      Contacts._ID + " limit 1")) {
            if (cursor == null) {
              LogUtil.w("Cp2LocalPhoneLookup.noContactsModifiedSince", "null cursor");
              LogUtil.w("Cp2DefaultDirectoryPhoneLookup.noContactsModifiedSince", "null cursor");
              return false;
            }
            return cursor.getCount() == 0;
@@ -413,7 +417,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
                      new String[] {Long.toString(lastModified)},
                      DeletedContacts.CONTACT_DELETED_TIMESTAMP + " limit 1")) {
            if (cursor == null) {
              LogUtil.w("Cp2LocalPhoneLookup.anyContactsDeletedSince", "null cursor");
              LogUtil.w("Cp2DefaultDirectoryPhoneLookup.anyContactsDeletedSince", "null cursor");
              return false;
            }
            return cursor.getCount() > 0;
@@ -423,12 +427,12 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {

  @Override
  public void setSubMessage(PhoneLookupInfo.Builder destination, Cp2Info subMessage) {
    destination.setCp2LocalInfo(subMessage);
    destination.setDefaultCp2Info(subMessage);
  }

  @Override
  public Cp2Info getSubMessage(PhoneLookupInfo phoneLookupInfo) {
    return phoneLookupInfo.getCp2LocalInfo();
    return phoneLookupInfo.getDefaultCp2Info();
  }

  @Override
@@ -712,7 +716,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
                  map.put(dialerPhoneNumber, ImmutableSet.of());
                }
                LogUtil.v(
                    "Cp2LocalPhoneLookup.buildMapForUpdatedOrAddedContacts",
                    "Cp2DefaultDirectoryPhoneLookup.buildMapForUpdatedOrAddedContacts",
                    "found %d numbers that may need updating",
                    updatedNumbers.size());
                return map;
@@ -735,7 +739,7 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
              queryPhoneTableBasedOnE164(
                  Cp2Projections.getProjectionForPhoneTable(), validE164Numbers)) {
            if (cursor == null) {
              LogUtil.w("Cp2LocalPhoneLookup.batchQueryForValidNumbers", "null cursor");
              LogUtil.w("Cp2DefaultDirectoryPhoneLookup.batchQueryForValidNumbers", "null cursor");
            } else {
              while (cursor.moveToNext()) {
                String validE164Number = Cp2Projections.getNormalizedNumberFromCursor(cursor);
@@ -764,7 +768,8 @@ public final class Cp2LocalPhoneLookup implements PhoneLookup<Cp2Info> {
          try (Cursor cursor =
              queryPhoneLookup(Cp2Projections.getProjectionForPhoneLookupTable(), invalidNumber)) {
            if (cursor == null) {
              LogUtil.w("Cp2LocalPhoneLookup.individualQueryForInvalidNumber", "null cursor");
              LogUtil.w(
                  "Cp2DefaultDirectoryPhoneLookup.individualQueryForInvalidNumber", "null cursor");
            } else {
              while (cursor.moveToNext()) {
                cp2ContactInfos.add(
Loading