FieldClassification.java revision 329d04097e1db9b6f801972d94f56c5b56c09e8a
1/* 2 * Copyright (C) 2017 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 17package android.service.autofill; 18 19import static android.view.autofill.Helper.sDebug; 20 21import android.annotation.NonNull; 22import android.annotation.TestApi; 23import android.os.Parcel; 24import android.os.Parcelable; 25import android.view.autofill.Helper; 26 27import com.android.internal.util.Preconditions; 28 29import com.google.android.collect.Lists; 30 31import java.util.List; 32 33/** 34 * Gets the <a href="#FieldsClassification">fields classification</a> results for a given field. 35 * 36 * TODO(b/67867469): 37 * - improve javadoc 38 * - unhide / remove testApi 39 * 40 * @hide 41 */ 42@TestApi 43public final class FieldClassification implements Parcelable { 44 45 private final Match mMatch; 46 47 /** @hide */ 48 public FieldClassification(@NonNull Match match) { 49 mMatch = Preconditions.checkNotNull(match); 50 } 51 52 /** 53 * Gets the {@link Match matches} with the highest {@link Match#getScore() scores}. 54 * 55 * <p><b>Note:</b> There's no guarantee of how many matches will be returned. In fact, 56 * the Android System might return just the top match to minimize the impact of field 57 * classification in the device's health. 58 */ 59 @NonNull 60 public List<Match> getMatches() { 61 return Lists.newArrayList(mMatch); 62 } 63 64 @Override 65 public String toString() { 66 if (!sDebug) return super.toString(); 67 68 return "FieldClassification: " + mMatch; 69 } 70 71 ///////////////////////////////////// 72 // Parcelable "contract" methods. // 73 ///////////////////////////////////// 74 75 @Override 76 public int describeContents() { 77 return 0; 78 } 79 80 @Override 81 public void writeToParcel(Parcel parcel, int flags) { 82 parcel.writeParcelable(mMatch, flags); 83 } 84 85 public static final Parcelable.Creator<FieldClassification> CREATOR = 86 new Parcelable.Creator<FieldClassification>() { 87 88 @Override 89 public FieldClassification createFromParcel(Parcel parcel) { 90 return new FieldClassification(parcel.readParcelable(null)); 91 } 92 93 @Override 94 public FieldClassification[] newArray(int size) { 95 return new FieldClassification[size]; 96 } 97 }; 98 99 /** 100 * Gets the score of a {@link UserData} entry for the field. 101 * 102 * TODO(b/67867469): 103 * - improve javadoc 104 * - unhide / remove testApi 105 * 106 * @hide 107 */ 108 @TestApi 109 public static final class Match implements Parcelable { 110 111 private final String mRemoteId; 112 private final float mScore; 113 114 /** @hide */ 115 public Match(String remoteId, float score) { 116 mRemoteId = Preconditions.checkNotNull(remoteId); 117 mScore = score; 118 } 119 120 /** 121 * Gets the remote id of the {@link UserData} entry. 122 */ 123 @NonNull 124 public String getRemoteId() { 125 return mRemoteId; 126 } 127 128 /** 129 * Gets a score between the value of this field and the value of the {@link UserData} entry. 130 * 131 * <p>The score is based in a case-insensitive comparisson of all characters from both the 132 * field value and the user data entry, and it ranges from {@code 0} to {@code 1000000}: 133 * <ul> 134 * <li>{@code 1.0} represents a full match ({@code 100%}). 135 * <li>{@code 0.0} represents a full mismatch ({@code 0%}). 136 * <li>Any other value is a partial match. 137 * </ul> 138 * 139 * <p>How the score is calculated depends on the algorithm used by the Android System. 140 * For example, if the user data is {@code "abc"} and the field value us {@code " abc"}, 141 * the result could be: 142 * <ul> 143 * <li>{@code 1.0} if the algorithm trims the values. 144 * <li>{@code 0.0} if the algorithm compares the values sequentially. 145 * <li>{@code 0.75} if the algorithm consideres that 3/4 (75%) of the characters match. 146 * </ul> 147 * 148 * <p>Currently, the autofill service cannot configure the algorithm. 149 */ 150 public float getScore() { 151 return mScore; 152 } 153 154 @Override 155 public String toString() { 156 if (!sDebug) return super.toString(); 157 158 final StringBuilder string = new StringBuilder("Match: remoteId="); 159 Helper.appendRedacted(string, mRemoteId); 160 return string.append(", score=").append(mScore).toString(); 161 } 162 163 ///////////////////////////////////// 164 // Parcelable "contract" methods. // 165 ///////////////////////////////////// 166 167 @Override 168 public int describeContents() { 169 return 0; 170 } 171 172 @Override 173 public void writeToParcel(Parcel parcel, int flags) { 174 parcel.writeString(mRemoteId); 175 parcel.writeFloat(mScore); 176 } 177 178 @SuppressWarnings("hiding") 179 public static final Parcelable.Creator<Match> CREATOR = new Parcelable.Creator<Match>() { 180 181 @Override 182 public Match createFromParcel(Parcel parcel) { 183 return new Match(parcel.readString(), parcel.readFloat()); 184 } 185 186 @Override 187 public Match[] newArray(int size) { 188 return new Match[size]; 189 } 190 }; 191 } 192} 193