• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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  */
16 
17 package com.android.bluetooth.pbapclient;
18 
19 import android.accounts.Account;
20 import android.content.Context;
21 import android.content.pm.PackageManager;
22 import android.content.res.Resources;
23 import android.database.Cursor;
24 import android.net.Uri;
25 import android.provider.CallLog.Calls;
26 import android.provider.ContactsContract;
27 import android.support.test.InstrumentationRegistry;
28 import android.support.test.filters.MediumTest;
29 import android.support.test.runner.AndroidJUnit4;
30 
31 import com.android.bluetooth.R;
32 
33 import org.junit.Assert;
34 import org.junit.Assume;
35 import org.junit.Before;
36 import org.junit.Test;
37 import org.junit.runner.RunWith;
38 
39 import java.io.IOException;
40 import java.io.InputStream;
41 import java.util.HashMap;
42 import java.util.TimeZone;
43 
44 @MediumTest
45 @RunWith(AndroidJUnit4.class)
46 public class PbapParserTest {
47     private Account mAccount;
48     private Resources mTestResources;
49     private Context mTargetContext;
50     private static final String TEST_ACCOUNT_NAME = "PBAPTESTACCOUNT";
51     private static final String TEST_PACKAGE_NAME = "com.android.bluetooth.tests";
52 
53     @Before
setUp()54     public void setUp() {
55         mTargetContext = InstrumentationRegistry.getTargetContext();
56         Assume.assumeTrue("Ignore test when PbapClientService is not enabled",
57                 mTargetContext.getResources().getBoolean(R.bool.profile_supported_pbapclient));
58         mAccount = new Account(TEST_ACCOUNT_NAME,
59                 mTargetContext.getString(com.android.bluetooth.R.string.pbap_account_type));
60         try {
61             mTestResources = mTargetContext.getPackageManager()
62                     .getResourcesForApplication(TEST_PACKAGE_NAME);
63         } catch (PackageManager.NameNotFoundException e) {
64             Assert.fail("Setup Failure Unable to get resources" + e.toString());
65         }
66         cleanupCallLog();
67         cleanupPhonebook();
68     }
69 
70     // testNoTimestamp should parse 1 poorly formed vcard and not crash.
71     @Test
testNoTimestamp()72     public void testNoTimestamp() throws IOException {
73         InputStream fileStream;
74         fileStream = mTestResources.openRawResource(
75                 com.android.bluetooth.tests.R.raw.no_timestamp_call_log);
76         BluetoothPbapVcardList pbapVCardList = new BluetoothPbapVcardList(mAccount, fileStream,
77                 PbapClientConnectionHandler.VCARD_TYPE_30);
78         Assert.assertEquals(1, pbapVCardList.getCount());
79         CallLogPullRequest processor =
80                 new CallLogPullRequest(mTargetContext, PbapClientConnectionHandler.MCH_PATH,
81                     new HashMap<>(), mAccount);
82         processor.setResults(pbapVCardList.getList());
83 
84         // Verify that these entries aren't in the call log to start.
85         Assert.assertFalse(verifyCallLog("555-0001", null, "3"));
86 
87         // Finish processing the data and verify entries were added to the call log.
88         processor.onPullComplete();
89         Assert.assertTrue(verifyCallLog("555-0001", null, "3"));
90     }
91 
92     // testMissedCall should parse one phonecall correctly.
93     @Test
testMissedCall()94     public void testMissedCall() throws IOException {
95         InputStream fileStream;
96         fileStream = mTestResources.openRawResource(
97                 com.android.bluetooth.tests.R.raw.single_missed_call);
98         BluetoothPbapVcardList pbapVCardList = new BluetoothPbapVcardList(mAccount, fileStream,
99                 PbapClientConnectionHandler.VCARD_TYPE_30);
100         Assert.assertEquals(1, pbapVCardList.getCount());
101         CallLogPullRequest processor =
102                 new CallLogPullRequest(mTargetContext, PbapClientConnectionHandler.MCH_PATH,
103                     new HashMap<>(), mAccount);
104         processor.setResults(pbapVCardList.getList());
105 
106         // Verify that these entries aren't in the call log to start.
107         Assert.assertFalse(verifyCallLog("555-0002", "1483232460000", "3"));
108         // Finish processing the data and verify entries were added to the call log.
109         processor.onPullComplete();
110         Assert.assertTrue(verifyCallLog("555-0002", "1483232460000", "3"));
111     }
112 
113     // testUnknownCall should parse two calls with no phone number.
114     @Test
testUnknownCall()115     public void testUnknownCall() throws IOException {
116         InputStream fileStream;
117         fileStream = mTestResources.openRawResource(
118                 com.android.bluetooth.tests.R.raw.unknown_number_call);
119         BluetoothPbapVcardList pbapVCardList = new BluetoothPbapVcardList(mAccount, fileStream,
120                 PbapClientConnectionHandler.VCARD_TYPE_30);
121         Assert.assertEquals(2, pbapVCardList.getCount());
122         CallLogPullRequest processor =
123                 new CallLogPullRequest(mTargetContext, PbapClientConnectionHandler.MCH_PATH,
124                     new HashMap<>(), mAccount);
125         processor.setResults(pbapVCardList.getList());
126 
127         // Verify that these entries aren't in the call log to start.
128         Assert.assertFalse(verifyCallLog("", "1483232520000", "3"));
129         Assert.assertFalse(verifyCallLog("", "1483232580000", "3"));
130 
131         // Finish processing the data and verify entries were added to the call log.
132         processor.onPullComplete();
133         Assert.assertTrue(verifyCallLog("", "1483232520000", "3"));
134         Assert.assertTrue(verifyCallLog("", "1483232580000", "3"));
135     }
136 
137     @Test
testPullPhoneBook()138     public void testPullPhoneBook() throws IOException {
139         InputStream fileStream;
140         fileStream = mTestResources.openRawResource(
141                 com.android.bluetooth.tests.R.raw.v30_simple);
142         BluetoothPbapVcardList pbapVCardList = new BluetoothPbapVcardList(mAccount, fileStream,
143                 PbapClientConnectionHandler.VCARD_TYPE_30);
144         Assert.assertEquals(1, pbapVCardList.getCount());
145         PhonebookPullRequest processor = new PhonebookPullRequest(mTargetContext, mAccount);
146         processor.setResults(pbapVCardList.getList());
147         Assert.assertFalse(verifyPhonebook("Roid And", "0300000000"));
148         processor.onPullComplete();
149         Assert.assertTrue(verifyPhonebook("Roid And", "0300000000"));
150     }
151 
cleanupCallLog()152     private void cleanupCallLog() {
153         mTargetContext.getContentResolver().delete(Calls.CONTENT_URI, null, null);
154     }
155 
cleanupPhonebook()156     private void cleanupPhonebook() {
157         mTargetContext.getContentResolver().delete(ContactsContract.RawContacts.CONTENT_URI,
158                 null, null);
159     }
160 
161     // Find Entries in call log with type matching number and date.
162     // If number or date is null it will match any number or date respectively.
verifyCallLog(String number, String date, String type)163     private boolean verifyCallLog(String number, String date, String type) {
164         String[] query = new String[]{Calls.NUMBER, Calls.DATE, Calls.TYPE};
165         Cursor cursor = mTargetContext.getContentResolver()
166                 .query(Calls.CONTENT_URI, query, Calls.TYPE + "= " + type, null,
167                         Calls.DATE + ", " + Calls.NUMBER);
168         if (date != null) {
169             date = adjDate(date);
170         }
171         if (cursor != null) {
172             while (cursor.moveToNext()) {
173                 String foundNumber = cursor.getString(cursor.getColumnIndex(Calls.NUMBER));
174                 String foundDate = cursor.getString(cursor.getColumnIndex(Calls.DATE));
175                 if ((number == null || number.equals(foundNumber)) && (date == null || date.equals(
176                         foundDate))) {
177                     return true;
178                 }
179             }
180             cursor.close();
181         }
182         return false;
183     }
184 
185     // Get time zone from device and adjust date to the device's time zone.
adjDate(String date)186     private static String adjDate(String date) {
187         TimeZone tz = TimeZone.getDefault();
188         long dt = Long.valueOf(date) - tz.getRawOffset();
189         return Long.toString(dt);
190     }
191 
verifyPhonebook(String name, String number)192     private boolean verifyPhonebook(String name, String number) {
193         Uri uri = Uri.withAppendedPath(ContactsContract.PhoneLookup.CONTENT_FILTER_URI,
194                 Uri.encode(number));
195         Cursor c = mTargetContext.getContentResolver().query(uri, null, null, null);
196         if (c != null && c.getCount() > 0) {
197             c.moveToNext();
198             String displayName = c.getString(
199                     c.getColumnIndex(ContactsContract.PhoneLookup.DISPLAY_NAME));
200             if (displayName.equals(name)) {
201                 return true;
202             }
203         }
204         return false;
205     }
206 
207 }
208