1 /*
<lambda>null2  * 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 package com.example.android.autofillframework.multidatasetservice
17 
18 import android.content.Context
19 import android.service.autofill.Dataset
20 import android.service.autofill.FillResponse
21 import android.service.autofill.SaveInfo
22 import android.support.annotation.DrawableRes
23 import android.util.Log
24 import android.view.View
25 import android.widget.RemoteViews
26 import com.example.android.autofillframework.CommonUtil.TAG
27 import com.example.android.autofillframework.R
28 import com.example.android.autofillframework.multidatasetservice.model.FilledAutofillFieldCollection
29 import java.util.HashMap
30 
31 
32 /**
33  * This is a class containing helper methods for building Autofill Datasets and Responses.
34  */
35 object AutofillHelper {
36 
37     /**
38      * Wraps autofill data in a [Dataset] object which can then be sent back to the
39      * client View.
40      */
41     fun newDataset(context: Context, autofillFieldMetadata: AutofillFieldMetadataCollection,
42             filledAutofillFieldCollection: FilledAutofillFieldCollection,
43             datasetAuth: Boolean): Dataset? {
44         filledAutofillFieldCollection.datasetName?.let { datasetName ->
45             val datasetBuilder: Dataset.Builder
46             if (datasetAuth) {
47                 datasetBuilder = Dataset.Builder(newRemoteViews(context.packageName, datasetName,
48                         R.drawable.ic_lock_black_24dp))
49                 val sender = AuthActivity.getAuthIntentSenderForDataset(context, datasetName)
50                 datasetBuilder.setAuthentication(sender)
51             } else {
52                 datasetBuilder = Dataset.Builder(newRemoteViews(context.packageName, datasetName,
53                         R.drawable.ic_person_black_24dp))
54             }
55             val setValueAtLeastOnce = filledAutofillFieldCollection
56                     .applyToFields(autofillFieldMetadata, datasetBuilder)
57             if (setValueAtLeastOnce) {
58                 return datasetBuilder.build()
59             }
60         }
61         return null
62     }
63 
64     fun newRemoteViews(packageName: String, remoteViewsText: String,
65             @DrawableRes drawableId: Int): RemoteViews {
66         val presentation = RemoteViews(packageName, R.layout.multidataset_service_list_item)
67         presentation.setTextViewText(R.id.text, remoteViewsText)
68         presentation.setImageViewResource(R.id.icon, drawableId)
69         return presentation
70     }
71 
72     /**
73      * Wraps autofill data in a [FillResponse] object (essentially a series of Datasets) which can
74      * then be sent back to the client View.
75      */
76     fun newResponse(context: Context,
77             datasetAuth: Boolean, autofillFieldMetadata: AutofillFieldMetadataCollection,
78             filledAutofillFieldCollectionMap: HashMap<String, FilledAutofillFieldCollection>?): FillResponse? {
79         val responseBuilder = FillResponse.Builder()
80         filledAutofillFieldCollectionMap?.keys?.let { datasetNames ->
81             for (datasetName in datasetNames) {
82                 filledAutofillFieldCollectionMap[datasetName]?.let { clientFormData ->
83                     val dataset = newDataset(context, autofillFieldMetadata, clientFormData, datasetAuth)
84                     dataset?.let(responseBuilder::addDataset)
85                 }
86             }
87         }
88         if (autofillFieldMetadata.saveType != 0) {
89             val autofillIds = autofillFieldMetadata.autofillIds
90             responseBuilder.setSaveInfo(SaveInfo.Builder(autofillFieldMetadata.saveType,
91                     autofillIds.toTypedArray()).build())
92             return responseBuilder.build()
93         } else {
94             Log.d(TAG, "These fields are not meant to be saved by autofill.")
95             return null
96         }
97     }
98 
99     fun isValidHint(hint: String): Boolean {
100         when (hint) {
101             View.AUTOFILL_HINT_CREDIT_CARD_EXPIRATION_DATE,
102             View.AUTOFILL_HINT_CREDIT_CARD_EXPIRATION_DAY,
103             View.AUTOFILL_HINT_CREDIT_CARD_EXPIRATION_MONTH,
104             View.AUTOFILL_HINT_CREDIT_CARD_EXPIRATION_YEAR,
105             View.AUTOFILL_HINT_CREDIT_CARD_NUMBER,
106             View.AUTOFILL_HINT_CREDIT_CARD_SECURITY_CODE,
107             View.AUTOFILL_HINT_EMAIL_ADDRESS,
108             View.AUTOFILL_HINT_PHONE,
109             View.AUTOFILL_HINT_NAME,
110             View.AUTOFILL_HINT_PASSWORD,
111             View.AUTOFILL_HINT_POSTAL_ADDRESS,
112             View.AUTOFILL_HINT_POSTAL_CODE,
113             View.AUTOFILL_HINT_USERNAME ->
114                 return true
115             else ->
116                 return false
117         }
118     }
119 }