diff options
3 files changed, 197 insertions, 5 deletions
diff --git a/src/com/android/providers/contacts/util/UserUtils.java b/src/com/android/providers/contacts/util/UserUtils.java index 2ed2750..0df5a24 100644 --- a/src/com/android/providers/contacts/util/UserUtils.java +++ b/src/com/android/providers/contacts/util/UserUtils.java @@ -17,8 +17,10 @@ package com.android.providers.contacts.util; import com.android.providers.contacts.ContactsProvider2; +import android.app.admin.DevicePolicyManager; import android.content.Context; import android.content.pm.UserInfo; +import android.os.UserHandle; import android.os.UserManager; import android.util.Log; @@ -34,6 +36,10 @@ public final class UserUtils { return (UserManager) context.getSystemService(Context.USER_SERVICE); } + private static DevicePolicyManager getDevicePolicyManager(Context context) { + return (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE); + } + public static int getCurrentUserHandle(Context context) { return getUserManager(context).getUserHandle(); } @@ -45,18 +51,26 @@ public final class UserUtils { public static int getCorpUserId(Context context) { final UserManager um = getUserManager(context); if (um == null) { - Log.w(TAG, "No user manager service found"); + Log.e(TAG, "No user manager service found"); return -1; } final int myUser = um.getUserHandle(); - // STOPSHIP Check the policy and make sure cross-user contacts lookup is allowed. b/16301261 - if (VERBOSE_LOGGING) { Log.v(TAG, "getCorpUserId: myUser=" + myUser); } + // TODO DevicePolicyManager is not mockable -- the constructor is private. + // Test it somehow. + if (getDevicePolicyManager(context) + .getCrossProfileCallerIdDisabled(new UserHandle(myUser))) { + if (VERBOSE_LOGGING) { + Log.v(TAG, "Enterprise caller-id disabled."); + } + return -1; + } + // Check each user. for (UserInfo ui : um.getUsers()) { if (!ui.isManagedProfile()) { diff --git a/tests/src/com/android/providers/contacts/ContactsActor.java b/tests/src/com/android/providers/contacts/ContactsActor.java index 8da2800..57dd45f 100644 --- a/tests/src/com/android/providers/contacts/ContactsActor.java +++ b/tests/src/com/android/providers/contacts/ContactsActor.java @@ -23,6 +23,7 @@ import android.accounts.AccountManagerFuture; import android.accounts.AuthenticatorException; import android.accounts.OnAccountsUpdateListener; import android.accounts.OperationCanceledException; +import android.app.admin.DevicePolicyManager; import android.content.ContentProvider; import android.content.ContentResolver; import android.content.ContentUris; @@ -33,6 +34,7 @@ import android.content.SharedPreferences; import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager; import android.content.pm.ProviderInfo; +import android.content.pm.UserInfo; import android.content.res.Configuration; import android.content.res.Resources; import android.database.Cursor; @@ -40,8 +42,12 @@ import android.location.Country; import android.location.CountryDetector; import android.location.CountryListener; import android.net.Uri; +import android.os.Bundle; import android.os.Handler; +import android.os.IUserManager; import android.os.Looper; +import android.os.UserHandle; +import android.os.UserManager; import android.provider.BaseColumns; import android.provider.ContactsContract; import android.provider.ContactsContract.AggregationExceptions; @@ -62,7 +68,9 @@ import com.google.android.collect.Sets; import java.io.File; import java.io.IOException; +import java.util.ArrayList; import java.util.Arrays; +import java.util.List; import java.util.Locale; import java.util.Set; @@ -135,6 +143,83 @@ public class ContactsActor { } } + public MockUserManager mockUserManager; + + public static class MockUserManager extends UserManager { + public static UserInfo createUserInfo(String name, int id, int groupId, int flags) { + final UserInfo ui = new UserInfo(); + ui.name = name; + ui.id = id; + ui.profileGroupId = groupId; + ui.flags = flags | UserInfo.FLAG_INITIALIZED; + return ui; + } + + public static final UserInfo PRIMARY_USER = createUserInfo("primary", 0, 0, + UserInfo.FLAG_PRIMARY | UserInfo.FLAG_ADMIN); + public static final UserInfo CORP_USER = createUserInfo("corp", 10, 0, + UserInfo.FLAG_MANAGED_PROFILE); + public static final UserInfo SECONDARY_USER = createUserInfo("2nd", 11, 11, 0); + + /** "My" user. Set it to change the current user. */ + public int myUser = 0; + + private ArrayList<UserInfo> mUsers = new ArrayList<>(); + + public MockUserManager(Context context) { + super(context, /* IUserManager */ null); + + mUsers.add(PRIMARY_USER); // Add the primary user. + } + + /** Replaces users. */ + public void setUsers(UserInfo... users) { + mUsers.clear(); + for (UserInfo ui : users) { + mUsers.add(ui); + } + } + + @Override + public int getUserHandle() { + return myUser; + } + + @Override + public UserInfo getUserInfo(int userHandle) { + for (UserInfo ui : mUsers) { + if (ui.id == userHandle) { + return ui; + } + } + return null; + } + + @Override + public UserInfo getProfileParent(int userHandle) { + final UserInfo child = getUserInfo(userHandle); + if (child == null) { + return null; + } + for (UserInfo ui : mUsers) { + if (ui.id != userHandle && ui.id == child.profileGroupId) { + return ui; + } + } + return null; + } + + @Override + public List<UserInfo> getUsers() { + return mUsers; + } + + @Override + public Bundle getUserRestrictions(UserHandle userHandle) { + return new Bundle(); + } + } + private IsolatedContext mProviderContext; /** @@ -143,7 +228,7 @@ public class ContactsActor { * a new instance of {@link RestrictionMockContext}, which stubs out the * security infrastructure. */ - public ContactsActor(Context overallContext, String packageName, + public ContactsActor(final Context overallContext, String packageName, Class<? extends ContentProvider> providerClass, String authority) throws Exception { resolver = new MockContentResolver(); context = new RestrictionMockContext(overallContext, packageName, resolver, @@ -177,7 +262,12 @@ public class ContactsActor { if (Context.ACCOUNT_SERVICE.equals(name)) { return mMockAccountManager; } - return super.getSystemService(name); + if (Context.USER_SERVICE.equals(name)) { + return mockUserManager; + } + // Use overallContext here; super.getSystemService() somehow won't return + // DevicePolicyManager. + return overallContext.getSystemService(name); } @Override @@ -187,9 +277,14 @@ public class ContactsActor { }; mMockAccountManager = new MockAccountManager(mProviderContext); + mockUserManager = new MockUserManager(mProviderContext); provider = addProvider(providerClass, authority); } + public Context getProviderContext() { + return mProviderContext; + } + public void addAuthority(String authority) { resolver.addProvider(authority, provider); } diff --git a/tests/src/com/android/providers/contacts/util/UserUtilsTest.java b/tests/src/com/android/providers/contacts/util/UserUtilsTest.java new file mode 100644 index 0000000..4417ad5 --- /dev/null +++ b/tests/src/com/android/providers/contacts/util/UserUtilsTest.java @@ -0,0 +1,83 @@ +/* + * Copyright (C) 2014 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License + */ +package com.android.providers.contacts.util; + +import com.android.providers.contacts.ContactsActor; +import com.android.providers.contacts.ContactsActor.MockUserManager; +import com.android.providers.contacts.SynchronousContactsProvider2; + +import android.content.ContentProvider; +import android.content.Context; +import android.os.UserManager; +import android.provider.ContactsContract; +import android.test.AndroidTestCase; +import android.test.suitebuilder.annotation.SmallTest; + +import static com.android.providers.contacts.ContactsActor.PACKAGE_GREY; + +@SmallTest +public class UserUtilsTest extends AndroidTestCase { + + protected ContactsActor mActor; + + @Override + protected void setUp() throws Exception { + super.setUp(); + + mActor = new ContactsActor(getContext(), PACKAGE_GREY, + SynchronousContactsProvider2.class, + ContactsContract.AUTHORITY); + } + + public void testGetCorpUserId() { + final Context c = mActor.getProviderContext(); + final MockUserManager um = mActor.mockUserManager; + + // No corp user. Primary only. + assertEquals(-1, UserUtils.getCorpUserId(c)); + + // Primary + corp + um.setUsers(MockUserManager.PRIMARY_USER, MockUserManager.CORP_USER); + + um.myUser = MockUserManager.PRIMARY_USER.id; + assertEquals(MockUserManager.CORP_USER.id, UserUtils.getCorpUserId(c)); + + um.myUser = MockUserManager.CORP_USER.id; + assertEquals(-1, UserUtils.getCorpUserId(c)); + + // Primary + secondary + corp + um.setUsers(MockUserManager.PRIMARY_USER, MockUserManager.SECONDARY_USER, + MockUserManager.CORP_USER); + + um.myUser = MockUserManager.PRIMARY_USER.id; + assertEquals(MockUserManager.CORP_USER.id, UserUtils.getCorpUserId(c)); + + um.myUser = MockUserManager.CORP_USER.id; + assertEquals(-1, UserUtils.getCorpUserId(c)); + + um.myUser = MockUserManager.SECONDARY_USER.id; + assertEquals(-1, UserUtils.getCorpUserId(c)); + + // Primary + secondary + um.setUsers(MockUserManager.PRIMARY_USER, MockUserManager.SECONDARY_USER); + + um.myUser = MockUserManager.PRIMARY_USER.id; + assertEquals(-1, UserUtils.getCorpUserId(c)); + + um.myUser = MockUserManager.SECONDARY_USER.id; + assertEquals(-1, UserUtils.getCorpUserId(c)); + } +} |