172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov/*
272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * Copyright (C) 2010 The Android Open Source Project
372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov *
472e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * Licensed under the Apache License, Version 2.0 (the "License");
572e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * you may not use this file except in compliance with the License.
672e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * You may obtain a copy of the License at
772e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov *
872e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov *      http://www.apache.org/licenses/LICENSE-2.0
972e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov *
1072e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * Unless required by applicable law or agreed to in writing, software
1172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * distributed under the License is distributed on an "AS IS" BASIS,
1272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * See the License for the specific language governing permissions and
1472e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * limitations under the License.
1572e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov */
1672e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovpackage com.android.providers.contacts;
1772e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
1872e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovimport android.content.Context;
1947fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Leeimport android.content.Intent;
2072e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovimport android.content.pm.ApplicationInfo;
2172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovimport android.content.pm.PackageInfo;
2272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovimport android.content.pm.PackageManager;
2347fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Leeimport android.content.pm.ResolveInfo;
24e0e24418cba10a5184e2966aaa32d5458fa6a387Dmitri Plotnikovimport android.content.res.Resources;
2572e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovimport android.os.Binder;
2672e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovimport android.test.mock.MockPackageManager;
2772e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
2847fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Leeimport java.util.ArrayList;
2972e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovimport java.util.HashMap;
3072e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovimport java.util.List;
3172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
3272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov/**
3372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * Mock {@link PackageManager} that knows about a specific set of packages
3472e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * to help test security models. Because {@link Binder#getCallingUid()}
3572e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * can't be mocked, you'll have to find your mock-UID manually using your
3672e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov * {@link Context#getPackageName()}.
3772e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov */
3872e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikovpublic class ContactsMockPackageManager extends MockPackageManager {
3972e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    private final HashMap<Integer, String> mForward = new HashMap<Integer, String>();
4072e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    private final HashMap<String, Integer> mReverse = new HashMap<String, Integer>();
4172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    private List<PackageInfo> mPackages;
4272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
4372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    public ContactsMockPackageManager() {
4472e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    }
4572e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
4672e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    /**
4772e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov     * Add a UID-to-package mapping, which is then stored internally.
4872e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov     */
4972e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    public void addPackage(int packageUid, String packageName) {
5072e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        mForward.put(packageUid, packageName);
5172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        mReverse.put(packageName, packageUid);
5272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    }
5372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
5447fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee    public void removePackage(int packageUid) {
5547fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee        final String packageName = mForward.remove(packageUid);
5647fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee        if (packageName != null) {
5747fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee            mReverse.remove(packageName);
5847fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee        }
5947fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee    }
6047fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee
6172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    @Override
6272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    public String getNameForUid(int uid) {
6372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        return "name-for-uid";
6472e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    }
6572e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
6672e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    @Override
6772e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    public String[] getPackagesForUid(int uid) {
6847fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee        final String packageName = mForward.get(uid);
6947fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee        if (packageName != null) {
7047fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee            return new String[] {packageName};
7147fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee        } else if (mPackages != null) {
7272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov            return new String[] { mPackages.get(0).packageName };
7372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        } else {
7447fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee            return new String[] {};
7572e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        }
7672e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    }
7772e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
7872e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    @Override
7972e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    public ApplicationInfo getApplicationInfo(String packageName, int flags) {
8072e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        ApplicationInfo info = new ApplicationInfo();
8172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        Integer uid = mReverse.get(packageName);
8272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        info.uid = (uid != null) ? uid : -1;
8372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        return info;
8472e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    }
8572e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
8672e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    public void setInstalledPackages(List<PackageInfo> packages) {
8772e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        this.mPackages = packages;
8872e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    }
8972e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
9072e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    @Override
9172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    public List<PackageInfo> getInstalledPackages(int flags) {
9272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        return mPackages;
9372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    }
9472e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov
9572e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    @Override
9672e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    public PackageInfo getPackageInfo(String packageName, int flags) throws NameNotFoundException {
9772e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        for (PackageInfo info : mPackages) {
9872e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov            if (info.packageName.equals(packageName)) {
9972e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov                return info;
10072e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov            }
10172e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        }
10272e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov        throw new NameNotFoundException();
10372e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov    }
104e0e24418cba10a5184e2966aaa32d5458fa6a387Dmitri Plotnikov
105e0e24418cba10a5184e2966aaa32d5458fa6a387Dmitri Plotnikov    @Override
10647fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee    public List<ResolveInfo> queryBroadcastReceivers(Intent intent, int flags) {
10747fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee        return new ArrayList<ResolveInfo>();
10847fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee    }
10947fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee
11047fc56dd40613fae565d0c4d630f5f0b5fc310ffYorke Lee    @Override
111e0e24418cba10a5184e2966aaa32d5458fa6a387Dmitri Plotnikov    public Resources getResourcesForApplication(String appPackageName) {
1120bf6b318e3c994294d4a885f57906debd4a0e64eDaniel Lehmann        return new ContactsMockResources();
113e0e24418cba10a5184e2966aaa32d5458fa6a387Dmitri Plotnikov    }
11472e3003a810fb4793a1513d17a40f8ab83d7d0afDmitri Plotnikov}
115