• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 android.app;
18 
19 import static com.google.common.truth.Truth.assertThat;
20 
21 import android.app.NotificationHistory.HistoricalNotification;
22 import android.graphics.drawable.Icon;
23 import android.os.Parcel;
24 import android.platform.test.annotations.Presubmit;
25 
26 import androidx.test.InstrumentationRegistry;
27 import androidx.test.ext.junit.runners.AndroidJUnit4;
28 
29 import org.junit.Test;
30 import org.junit.runner.RunWith;
31 
32 import java.util.ArrayList;
33 import java.util.Arrays;
34 import java.util.HashSet;
35 import java.util.List;
36 import java.util.Set;
37 
38 @RunWith(AndroidJUnit4.class)
39 @Presubmit
40 public class NotificationHistoryTest {
41 
getHistoricalNotification(int index)42     private static HistoricalNotification getHistoricalNotification(int index) {
43         return getHistoricalNotification("package" + index, index);
44     }
45 
getHistoricalNotification(String packageName, int index)46     private static HistoricalNotification getHistoricalNotification(String packageName, int index) {
47         return getHistoricalNotification(packageName, index, /* includeIcon= */ true);
48     }
49 
getHistoricalNotification(String packageName, int index, boolean includeIcon)50     private static HistoricalNotification getHistoricalNotification(String packageName, int index,
51             boolean includeIcon) {
52         String expectedChannelName = "channelName" + index;
53         String expectedChannelId = "channelId" + index;
54         int expectedUid = 1123456 + index;
55         int expectedUserId = 11 + index;
56         long expectedPostTime = 987654321 + index;
57         String expectedTitle = "title" + index;
58         String expectedText = "text" + index;
59         Icon expectedIcon = Icon.createWithResource(InstrumentationRegistry.getContext(),
60                 index);
61         String conversationId = null;
62         if (index % 2 == 0) {
63             conversationId = "convo" + index;
64         }
65 
66         return new HistoricalNotification.Builder()
67                 .setPackage(packageName)
68                 .setChannelName(expectedChannelName)
69                 .setChannelId(expectedChannelId)
70                 .setUid(expectedUid)
71                 .setUserId(expectedUserId)
72                 .setPostedTimeMs(expectedPostTime)
73                 .setTitle(expectedTitle)
74                 .setText(expectedText)
75                 .setIcon(includeIcon ? expectedIcon : null)
76                 .setConversationId(conversationId)
77                 .build();
78     }
79 
80     @Test
testHistoricalNotificationBuilder()81     public void testHistoricalNotificationBuilder() {
82         String expectedPackage = "package";
83         String expectedChannelName = "channelName";
84         String expectedChannelId = "channelId";
85         int expectedUid = 1123456;
86         int expectedUserId = 11;
87         long expectedPostTime = 987654321;
88         String expectedTitle = "title";
89         String expectedText = "text";
90         Icon expectedIcon = Icon.createWithResource(InstrumentationRegistry.getContext(),
91                 android.R.drawable.btn_star);
92         String expectedConversationId = "convo";
93 
94         HistoricalNotification n = new HistoricalNotification.Builder()
95                 .setPackage(expectedPackage)
96                 .setChannelName(expectedChannelName)
97                 .setChannelId(expectedChannelId)
98                 .setUid(expectedUid)
99                 .setUserId(expectedUserId)
100                 .setPostedTimeMs(expectedPostTime)
101                 .setTitle(expectedTitle)
102                 .setText(expectedText)
103                 .setIcon(expectedIcon)
104                 .setConversationId(expectedConversationId)
105                 .build();
106 
107         assertThat(n.getPackage()).isEqualTo(expectedPackage);
108         assertThat(n.getChannelName()).isEqualTo(expectedChannelName);
109         assertThat(n.getChannelId()).isEqualTo(expectedChannelId);
110         assertThat(n.getUid()).isEqualTo(expectedUid);
111         assertThat(n.getUserId()).isEqualTo(expectedUserId);
112         assertThat(n.getPostedTimeMs()).isEqualTo(expectedPostTime);
113         assertThat(n.getTitle()).isEqualTo(expectedTitle);
114         assertThat(n.getText()).isEqualTo(expectedText);
115         assertThat(expectedIcon.sameAs(n.getIcon())).isTrue();
116         assertThat(n.getConversationId()).isEqualTo(expectedConversationId);
117     }
118 
119     @Test
testAddNotificationToWrite()120     public void testAddNotificationToWrite() {
121         NotificationHistory history = new NotificationHistory();
122         HistoricalNotification n = getHistoricalNotification(0);
123         HistoricalNotification n2 = getHistoricalNotification(1);
124 
125         history.addNotificationToWrite(n2);
126         history.addNotificationToWrite(n);
127 
128         assertThat(history.getNotificationsToWrite().size()).isEqualTo(2);
129         assertThat(history.getNotificationsToWrite().get(0)).isSameInstanceAs(n2);
130         assertThat(history.getNotificationsToWrite().get(1)).isSameInstanceAs(n);
131         assertThat(history.getHistoryCount()).isEqualTo(2);
132     }
133 
134     @Test
testAddNotificationsToWrite()135     public void testAddNotificationsToWrite() {
136         NotificationHistory history = new NotificationHistory();
137         HistoricalNotification n = getHistoricalNotification(3);
138         HistoricalNotification n2 = getHistoricalNotification(1);
139         HistoricalNotification n5 = getHistoricalNotification(0);
140         history.addNotificationToWrite(n2);
141         history.addNotificationToWrite(n);
142         history.addNotificationToWrite(n5);
143 
144         NotificationHistory secondHistory = new NotificationHistory();
145         HistoricalNotification n3 = getHistoricalNotification(4);
146         HistoricalNotification n4 = getHistoricalNotification(2);
147         secondHistory.addNotificationToWrite(n4);
148         secondHistory.addNotificationToWrite(n3);
149 
150         history.addNotificationsToWrite(secondHistory);
151 
152         assertThat(history.getNotificationsToWrite().size()).isEqualTo(5);
153         assertThat(history.getNotificationsToWrite().get(0)).isSameInstanceAs(n3);
154         assertThat(history.getNotificationsToWrite().get(1)).isSameInstanceAs(n);
155         assertThat(history.getNotificationsToWrite().get(2)).isSameInstanceAs(n4);
156         assertThat(history.getNotificationsToWrite().get(3)).isSameInstanceAs(n2);
157         assertThat(history.getNotificationsToWrite().get(4)).isSameInstanceAs(n5);
158         assertThat(history.getHistoryCount()).isEqualTo(5);
159 
160         assertThat(history.getPooledStringsToWrite()).asList().contains(n2.getChannelName());
161         assertThat(history.getPooledStringsToWrite()).asList().contains(n4.getPackage());
162     }
163 
164     @Test
testPoolStringsFromNotifications()165     public void testPoolStringsFromNotifications() {
166         NotificationHistory history = new NotificationHistory();
167 
168         List<String> expectedStrings = new ArrayList<>();
169         for (int i = 1; i <= 10; i++) {
170             HistoricalNotification n = getHistoricalNotification(i);
171             expectedStrings.add(n.getPackage());
172             expectedStrings.add(n.getChannelName());
173             expectedStrings.add(n.getChannelId());
174             if (n.getConversationId() != null) {
175                 expectedStrings.add(n.getConversationId());
176             }
177             history.addNotificationToWrite(n);
178         }
179 
180         history.poolStringsFromNotifications();
181 
182         assertThat(history.getPooledStringsToWrite().length).isEqualTo(expectedStrings.size());
183         String previous = null;
184         for (String actual : history.getPooledStringsToWrite()) {
185             assertThat(expectedStrings).contains(actual);
186 
187             if (previous != null) {
188                 assertThat(actual).isGreaterThan(previous);
189             }
190             previous = actual;
191         }
192     }
193 
194     @Test
testAddPooledStrings()195     public void testAddPooledStrings() {
196         NotificationHistory history = new NotificationHistory();
197 
198         List<String> expectedStrings = new ArrayList<>();
199         for (int i = 1; i <= 10; i++) {
200             HistoricalNotification n = getHistoricalNotification(i);
201             expectedStrings.add(n.getPackage());
202             expectedStrings.add(n.getChannelName());
203             expectedStrings.add(n.getChannelId());
204             if (n.getConversationId() != null) {
205                 expectedStrings.add(n.getConversationId());
206             }
207             history.addNotificationToWrite(n);
208         }
209 
210         history.addPooledStrings(expectedStrings);
211 
212         String[] actualStrings = history.getPooledStringsToWrite();
213         assertThat(actualStrings.length).isEqualTo(expectedStrings.size());
214         String previous = null;
215         for (String actual : actualStrings) {
216             assertThat(expectedStrings).contains(actual);
217 
218             if (previous != null) {
219                 assertThat(actual).isGreaterThan(previous);
220             }
221             previous = actual;
222         }
223     }
224 
225     @Test
testRemoveNotificationsFromWrite()226     public void testRemoveNotificationsFromWrite() {
227         NotificationHistory history = new NotificationHistory();
228 
229         List<HistoricalNotification> postRemoveExpectedEntries = new ArrayList<>();
230         List<String> postRemoveExpectedStrings = new ArrayList<>();
231         for (int i = 1; i <= 10; i++) {
232             HistoricalNotification n =
233                     getHistoricalNotification((i % 2 == 0) ? "pkgEven" : "pkgOdd", i);
234 
235             if (i % 2 == 0) {
236                 postRemoveExpectedStrings.add(n.getPackage());
237                 postRemoveExpectedStrings.add(n.getChannelName());
238                 postRemoveExpectedStrings.add(n.getChannelId());
239                 if (n.getConversationId() != null) {
240                     postRemoveExpectedStrings.add(n.getConversationId());
241                 }
242                 postRemoveExpectedEntries.add(n);
243             }
244 
245             history.addNotificationToWrite(n);
246         }
247 
248         history.poolStringsFromNotifications();
249 
250         assertThat(history.getNotificationsToWrite().size()).isEqualTo(10);
251         // 2 package names and 10 * 2 unique channel names and ids and 5 conversation ids
252         assertThat(history.getPooledStringsToWrite().length).isEqualTo(27);
253 
254         history.removeNotificationsFromWrite("pkgOdd");
255 
256 
257         // 1 package names and 5 * 2 unique channel names and ids and 5 conversation ids
258         assertThat(history.getPooledStringsToWrite().length).isEqualTo(16);
259         assertThat(history.getNotificationsToWrite())
260                 .containsExactlyElementsIn(postRemoveExpectedEntries);
261     }
262 
263     @Test
testRemoveNotificationFromWrite()264     public void testRemoveNotificationFromWrite() {
265         NotificationHistory history = new NotificationHistory();
266 
267         List<HistoricalNotification> postRemoveExpectedEntries = new ArrayList<>();
268         List<String> postRemoveExpectedStrings = new ArrayList<>();
269         for (int i = 1; i <= 10; i++) {
270             HistoricalNotification n = getHistoricalNotification("pkg", i);
271 
272             if (987654323 != n.getPostedTimeMs()) {
273                 postRemoveExpectedStrings.add(n.getPackage());
274                 postRemoveExpectedStrings.add(n.getChannelName());
275                 postRemoveExpectedStrings.add(n.getChannelId());
276                 if (n.getConversationId() != null) {
277                     postRemoveExpectedStrings.add(n.getConversationId());
278                 }
279                 postRemoveExpectedEntries.add(n);
280             }
281 
282             history.addNotificationToWrite(n);
283         }
284 
285         history.poolStringsFromNotifications();
286 
287         assertThat(history.getNotificationsToWrite().size()).isEqualTo(10);
288         // 1 package name and 20 unique channel names and ids and 5 conversation ids
289         assertThat(history.getPooledStringsToWrite().length).isEqualTo(26);
290 
291         history.removeNotificationFromWrite("pkg", 987654323);
292 
293 
294         // 1 package names and 9 * 2 unique channel names and ids and 4 conversation ids
295         assertThat(history.getPooledStringsToWrite().length).isEqualTo(23);
296         assertThat(history.getNotificationsToWrite())
297                 .containsExactlyElementsIn(postRemoveExpectedEntries);
298     }
299 
300     @Test
testRemoveConversationNotificationFromWrite()301     public void testRemoveConversationNotificationFromWrite() {
302         NotificationHistory history = new NotificationHistory();
303 
304         List<HistoricalNotification> postRemoveExpectedEntries = new ArrayList<>();
305         List<String> postRemoveExpectedStrings = new ArrayList<>();
306         for (int i = 1; i <= 10; i++) {
307             HistoricalNotification n = getHistoricalNotification("pkg", i);
308 
309             if (i != 2 && i != 4) {
310                 postRemoveExpectedStrings.add(n.getPackage());
311                 postRemoveExpectedStrings.add(n.getChannelName());
312                 postRemoveExpectedStrings.add(n.getChannelId());
313                 if (n.getConversationId() != null) {
314                     postRemoveExpectedStrings.add(n.getConversationId());
315                 }
316                 postRemoveExpectedEntries.add(n);
317             }
318 
319             history.addNotificationToWrite(n);
320         }
321         // add second notification with the same conversation id that will be removed
322         history.addNotificationToWrite(getHistoricalNotification("pkg", 2));
323 
324         history.poolStringsFromNotifications();
325 
326         assertThat(history.getNotificationsToWrite().size()).isEqualTo(11);
327         // 1 package name and 20 unique channel names and ids and 5 conversation ids
328         assertThat(history.getPooledStringsToWrite().length).isEqualTo(26);
329 
330         history.removeConversationsFromWrite("pkg", Set.of("convo2", "convo4"));
331 
332         // 1 package names and 8 * 2 unique channel names and ids and 3 conversation ids
333         assertThat(history.getPooledStringsToWrite().length).isEqualTo(20);
334         assertThat(history.getNotificationsToWrite())
335                 .containsExactlyElementsIn(postRemoveExpectedEntries);
336     }
337 
338     @Test
testRemoveChannelFromWrite()339     public void testRemoveChannelFromWrite() {
340         NotificationHistory history = new NotificationHistory();
341 
342         List<HistoricalNotification> postRemoveExpectedEntries = new ArrayList<>();
343         Set<String> postRemoveExpectedStrings = new HashSet<>();
344         for (int i = 1; i <= 10; i++) {
345             HistoricalNotification n = getHistoricalNotification("pkg", i);
346 
347             // Remove channel numbers 5 and 6
348             if (i != 5 && i != 6) {
349                 postRemoveExpectedStrings.add(n.getPackage());
350                 postRemoveExpectedStrings.add(n.getChannelName());
351                 postRemoveExpectedStrings.add(n.getChannelId());
352                 if (n.getConversationId() != null) {
353                     postRemoveExpectedStrings.add(n.getConversationId());
354                 }
355                 postRemoveExpectedEntries.add(n);
356             }
357 
358             history.addNotificationToWrite(n);
359         }
360         // add second notification with the same channel id that will also be removed
361         history.addNotificationToWrite(getHistoricalNotification("pkg", 6));
362 
363         history.poolStringsFromNotifications();
364 
365         assertThat(history.getNotificationsToWrite().size()).isEqualTo(11);
366         // 1 package name and 20 unique channel names and ids and 5 conversation ids
367         assertThat(history.getPooledStringsToWrite().length).isEqualTo(26);
368 
369         history.removeChannelFromWrite("pkg", "channelId5");
370         history.removeChannelFromWrite("pkg", "channelId6");
371 
372         // 1 package names and 8 * 2 unique channel names and ids and 4 conversation ids
373         assertThat(history.getPooledStringsToWrite().length).isEqualTo(21);
374         assertThat(Arrays.asList(history.getPooledStringsToWrite()))
375                 .containsExactlyElementsIn(postRemoveExpectedStrings);
376         assertThat(history.getNotificationsToWrite())
377                 .containsExactlyElementsIn(postRemoveExpectedEntries);
378     }
379 
380     @Test
testParceling()381     public void testParceling() {
382         NotificationHistory history = new NotificationHistory();
383 
384         List<HistoricalNotification> expectedEntries = new ArrayList<>();
385         for (int i = 10; i >= 1; i--) {
386             HistoricalNotification n = getHistoricalNotification("packageName" + i,
387                     i, /* includeIcon= */ false);
388             expectedEntries.add(n);
389             history.addNotificationToWrite(n);
390         }
391         history.poolStringsFromNotifications();
392 
393         Parcel parcel = Parcel.obtain();
394         history.writeToParcel(parcel, 0);
395         parcel.setDataPosition(0);
396         NotificationHistory parceledHistory = NotificationHistory.CREATOR.createFromParcel(parcel);
397 
398         assertThat(parceledHistory.getHistoryCount()).isEqualTo(expectedEntries.size());
399 
400         for (int i = 0; i < expectedEntries.size(); i++) {
401             assertThat(parceledHistory.hasNextNotification()).isTrue();
402 
403             HistoricalNotification postParcelNotification = parceledHistory.getNextNotification();
404             assertThat(postParcelNotification).isEqualTo(expectedEntries.get(i));
405         }
406         assertThat(parceledHistory.hasNextNotification()).isFalse();
407         assertThat(parceledHistory.getNextNotification()).isNull();
408     }
409 }
410