ExternalSourcesDetails.java revision 7e59ec499c633162297344ef2d318ca80fb09f28
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 */
16package com.android.settings.applications;
17
18import android.app.AlertDialog;
19import android.app.AppOpsManager;
20import android.content.Context;
21import android.os.Bundle;
22import android.os.UserHandle;
23import android.os.UserManager;
24import android.support.v7.preference.Preference;
25import android.support.v7.preference.Preference.OnPreferenceChangeListener;
26
27import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
28import com.android.settings.R;
29import com.android.settings.Settings;
30import com.android.settings.applications.AppStateInstallAppsBridge.InstallAppsState;
31import com.android.settingslib.RestrictedSwitchPreference;
32import com.android.settingslib.applications.ApplicationsState.AppEntry;
33
34import static android.app.Activity.RESULT_CANCELED;
35import static android.app.Activity.RESULT_OK;
36
37public class ExternalSourcesDetails extends AppInfoWithHeader
38        implements OnPreferenceChangeListener {
39
40    private static final String KEY_EXTERNAL_SOURCE_SWITCH = "external_sources_settings_switch";
41
42    private AppStateInstallAppsBridge mAppBridge;
43    private AppOpsManager mAppOpsManager;
44    private UserManager mUserManager;
45    private RestrictedSwitchPreference mSwitchPref;
46    private InstallAppsState mInstallAppsState;
47
48    @Override
49    public void onCreate(Bundle savedInstanceState) {
50        super.onCreate(savedInstanceState);
51
52        final Context context = getActivity();
53        mAppBridge = new AppStateInstallAppsBridge(context, mState, null);
54        mAppOpsManager = (AppOpsManager) context.getSystemService(Context.APP_OPS_SERVICE);
55        mUserManager = UserManager.get(context);
56
57        addPreferencesFromResource(R.xml.external_sources_details);
58        mSwitchPref = (RestrictedSwitchPreference) findPreference(KEY_EXTERNAL_SOURCE_SWITCH);
59        mSwitchPref.setOnPreferenceChangeListener(this);
60    }
61
62    @Override
63    public boolean onPreferenceChange(Preference preference, Object newValue) {
64        final boolean checked = (Boolean) newValue;
65        if (preference == mSwitchPref) {
66            if (mInstallAppsState != null && checked != mInstallAppsState.canInstallApps()) {
67                if (Settings.ManageAppExternalSourcesActivity.class.getName().equals(
68                        getIntent().getComponent().getClassName())) {
69                    setResult(checked ? RESULT_OK : RESULT_CANCELED);
70                }
71                setCanInstallApps(checked);
72                refreshUi();
73            }
74            return true;
75        }
76        return false;
77    }
78
79    static CharSequence getPreferenceSummary(Context context, AppEntry entry) {
80        final UserManager um = UserManager.get(context);
81        final int userRestrictionSource = um.getUserRestrictionSource(
82                UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES,
83                UserHandle.getUserHandleForUid(entry.info.uid));
84        switch (userRestrictionSource) {
85            case UserManager.RESTRICTION_SOURCE_DEVICE_OWNER:
86            case UserManager.RESTRICTION_SOURCE_PROFILE_OWNER:
87                return context.getString(R.string.disabled_by_admin);
88            case UserManager.RESTRICTION_SOURCE_SYSTEM:
89                return context.getString(R.string.disabled);
90        }
91
92        final InstallAppsState appsState = new AppStateInstallAppsBridge(context, null, null)
93                .createInstallAppsStateFor(entry.info.packageName, entry.info.uid);
94
95        return context.getString(appsState.canInstallApps()
96                ? R.string.app_permission_summary_allowed
97                : R.string.app_permission_summary_not_allowed);
98    }
99
100    private void setCanInstallApps(boolean newState) {
101        mAppOpsManager.setMode(AppOpsManager.OP_REQUEST_INSTALL_PACKAGES,
102                mPackageInfo.applicationInfo.uid, mPackageName,
103                newState ? AppOpsManager.MODE_ALLOWED : AppOpsManager.MODE_ERRORED);
104    }
105
106    @Override
107    protected boolean refreshUi() {
108        if (mUserManager.hasBaseUserRestriction(UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES,
109                UserHandle.of(UserHandle.myUserId()))) {
110            mSwitchPref.setChecked(false);
111            mSwitchPref.setSummary(R.string.disabled);
112            mSwitchPref.setEnabled(false);
113            return true;
114        }
115        mSwitchPref.checkRestrictionAndSetDisabled(UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES);
116        if (mSwitchPref.isDisabledByAdmin()) {
117            return true;
118        }
119        mInstallAppsState = mAppBridge.createInstallAppsStateFor(mPackageName,
120                mPackageInfo.applicationInfo.uid);
121        if (!mInstallAppsState.isPotentialAppSource()) {
122            // Invalid app entry. Should not allow changing permission
123            mSwitchPref.setEnabled(false);
124            return true;
125        }
126        mSwitchPref.setChecked(mInstallAppsState.canInstallApps());
127        return true;
128    }
129
130    @Override
131    protected AlertDialog createDialog(int id, int errorCode) {
132        return null;
133    }
134
135    @Override
136    public int getMetricsCategory() {
137        return MetricsEvent.MANAGE_EXTERNAL_SOURCES;
138    }
139}
140