1 /*
2  * Copyright (C) 2019 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.packageinstaller.role.service;
18 
19 import android.content.Context;
20 import android.database.Cursor;
21 import android.database.MatrixCursor;
22 import android.os.Binder;
23 import android.provider.SearchIndexablesContract;
24 import android.util.ArrayMap;
25 
26 import androidx.annotation.Nullable;
27 
28 import com.android.packageinstaller.permission.service.BaseSearchIndexablesProvider;
29 import com.android.packageinstaller.role.model.Role;
30 import com.android.packageinstaller.role.model.Roles;
31 import com.android.permissioncontroller.R;
32 
33 /**
34  * {@link android.provider.SearchIndexablesProvider} for roles.
35  */
36 public class RoleSearchIndexablesProvider extends BaseSearchIndexablesProvider {
37 
38     public static final String ACTION_MANAGE_DEFAULT_APP =
39             "com.android.permissioncontroller.settingssearch.action.MANAGE_DEFAULT_APP";
40 
41     public static final String ACTION_MANAGE_SPECIAL_APP_ACCESS =
42             "com.android.permissioncontroller.settingssearch.action.MANAGE_SPECIAL_APP_ACCESS";
43 
44     @Nullable
45     @Override
queryRawData(@ullable String[] projection)46     public Cursor queryRawData(@Nullable String[] projection) {
47         MatrixCursor cursor = new MatrixCursor(SearchIndexablesContract.INDEXABLES_RAW_COLUMNS);
48         Context context = getContext();
49         ArrayMap<String, Role> roles = Roles.get(context);
50         int rolesSize = roles.size();
51         for (int i = 0; i < rolesSize; i++) {
52             Role role = roles.valueAt(i);
53 
54             long token = Binder.clearCallingIdentity();
55             try {
56                 if (!role.isAvailable(context) || !role.isVisible(context)) {
57                     continue;
58                 }
59             } finally {
60                 Binder.restoreCallingIdentity(token);
61             }
62 
63             String label = context.getString(role.getLabelResource());
64             boolean isExclusive = role.isExclusive();
65             cursor.newRow()
66                     .add(SearchIndexablesContract.RawData.COLUMN_RANK, 0)
67                     .add(SearchIndexablesContract.RawData.COLUMN_TITLE, label)
68                     .add(SearchIndexablesContract.RawData.COLUMN_KEYWORDS, label + ", "
69                             + getContext().getString(isExclusive
70                             ? R.string.default_app_search_keyword
71                             : R.string.special_app_access_search_keyword))
72                     .add(SearchIndexablesContract.RawData.COLUMN_KEY, createRawDataKey(
73                             role.getName(), context))
74                     .add(SearchIndexablesContract.RawData.COLUMN_INTENT_ACTION, isExclusive
75                             ? ACTION_MANAGE_DEFAULT_APP : ACTION_MANAGE_SPECIAL_APP_ACCESS);
76         }
77         return cursor;
78     }
79 }
80