1/* 2 * Copyright (C) 2016 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 17package com.android.server.connectivity; 18 19import static com.android.server.connectivity.NetworkNotificationManager.NotificationType.*; 20import static org.mockito.Mockito.any; 21import static org.mockito.Mockito.anyInt; 22import static org.mockito.Mockito.eq; 23import static org.mockito.Mockito.never; 24import static org.mockito.Mockito.reset; 25import static org.mockito.Mockito.times; 26import static org.mockito.Mockito.verify; 27import static org.mockito.Mockito.when; 28 29import android.app.Notification; 30import android.app.NotificationManager; 31import android.content.Context; 32import android.content.pm.ApplicationInfo; 33import android.content.pm.PackageManager; 34import android.content.res.Resources; 35import android.net.NetworkCapabilities; 36import android.net.NetworkInfo; 37import android.support.test.runner.AndroidJUnit4; 38import android.support.test.filters.SmallTest; 39import android.telephony.TelephonyManager; 40 41import com.android.server.connectivity.NetworkNotificationManager.NotificationType; 42 43import java.util.ArrayList; 44import java.util.Arrays; 45import java.util.Collections; 46import java.util.List; 47 48import org.junit.runner.RunWith; 49import org.junit.Before; 50import org.junit.Test; 51import org.mockito.ArgumentCaptor; 52import org.mockito.Mock; 53import org.mockito.Mockito; 54import org.mockito.MockitoAnnotations; 55 56 57@RunWith(AndroidJUnit4.class) 58@SmallTest 59public class NetworkNotificationManagerTest { 60 61 static final NetworkCapabilities CELL_CAPABILITIES = new NetworkCapabilities(); 62 static final NetworkCapabilities WIFI_CAPABILITIES = new NetworkCapabilities(); 63 static { 64 CELL_CAPABILITIES.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR); 65 CELL_CAPABILITIES.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET); 66 67 WIFI_CAPABILITIES.addTransportType(NetworkCapabilities.TRANSPORT_WIFI); 68 WIFI_CAPABILITIES.addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET); 69 } 70 71 @Mock Context mCtx; 72 @Mock Resources mResources; 73 @Mock PackageManager mPm; 74 @Mock TelephonyManager mTelephonyManager; 75 @Mock NotificationManager mNotificationManager; 76 @Mock NetworkAgentInfo mWifiNai; 77 @Mock NetworkAgentInfo mCellNai; 78 @Mock NetworkInfo mNetworkInfo; 79 ArgumentCaptor<Notification> mCaptor; 80 81 NetworkNotificationManager mManager; 82 83 @Before 84 public void setUp() { 85 MockitoAnnotations.initMocks(this); 86 mCaptor = ArgumentCaptor.forClass(Notification.class); 87 mWifiNai.networkCapabilities = WIFI_CAPABILITIES; 88 mWifiNai.networkInfo = mNetworkInfo; 89 mCellNai.networkCapabilities = CELL_CAPABILITIES; 90 mCellNai.networkInfo = mNetworkInfo; 91 when(mCtx.getResources()).thenReturn(mResources); 92 when(mCtx.getPackageManager()).thenReturn(mPm); 93 when(mCtx.getApplicationInfo()).thenReturn(new ApplicationInfo()); 94 when(mNetworkInfo.getExtraInfo()).thenReturn("extra"); 95 when(mResources.getColor(anyInt(), any())).thenReturn(0xFF607D8B); 96 97 mManager = new NetworkNotificationManager(mCtx, mTelephonyManager, mNotificationManager); 98 } 99 100 @Test 101 public void testNotificationsShownAndCleared() { 102 final int NETWORK_ID_BASE = 100; 103 List<NotificationType> types = Arrays.asList(NotificationType.values()); 104 List<Integer> ids = new ArrayList<>(types.size()); 105 for (int i = 0; i < types.size(); i++) { 106 ids.add(NETWORK_ID_BASE + i); 107 } 108 Collections.shuffle(ids); 109 Collections.shuffle(types); 110 111 for (int i = 0; i < ids.size(); i++) { 112 mManager.showNotification(ids.get(i), types.get(i), mWifiNai, mCellNai, null, false); 113 } 114 115 List<Integer> idsToClear = new ArrayList<>(ids); 116 Collections.shuffle(idsToClear); 117 for (int i = 0; i < ids.size(); i++) { 118 mManager.clearNotification(idsToClear.get(i)); 119 } 120 121 for (int i = 0; i < ids.size(); i++) { 122 final int id = ids.get(i); 123 final int eventId = types.get(i).eventId; 124 final String tag = NetworkNotificationManager.tagFor(id); 125 verify(mNotificationManager, times(1)).notifyAsUser(eq(tag), eq(eventId), any(), any()); 126 verify(mNotificationManager, times(1)).cancelAsUser(eq(tag), eq(eventId), any()); 127 } 128 } 129 130 @Test 131 public void testNoInternetNotificationsNotShownForCellular() { 132 mManager.showNotification(100, NO_INTERNET, mCellNai, mWifiNai, null, false); 133 mManager.showNotification(101, LOST_INTERNET, mCellNai, mWifiNai, null, false); 134 135 verify(mNotificationManager, never()).notifyAsUser(any(), anyInt(), any(), any()); 136 137 mManager.showNotification(102, NO_INTERNET, mWifiNai, mCellNai, null, false); 138 139 final int eventId = NO_INTERNET.eventId; 140 final String tag = NetworkNotificationManager.tagFor(102); 141 verify(mNotificationManager, times(1)).notifyAsUser(eq(tag), eq(eventId), any(), any()); 142 } 143 144 @Test 145 public void testNotificationsNotShownIfNoInternetCapability() { 146 mWifiNai.networkCapabilities = new NetworkCapabilities(); 147 mWifiNai.networkCapabilities .addTransportType(NetworkCapabilities.TRANSPORT_WIFI); 148 mManager.showNotification(102, NO_INTERNET, mWifiNai, mCellNai, null, false); 149 mManager.showNotification(103, LOST_INTERNET, mWifiNai, mCellNai, null, false); 150 mManager.showNotification(104, NETWORK_SWITCH, mWifiNai, mCellNai, null, false); 151 152 verify(mNotificationManager, never()).notifyAsUser(any(), anyInt(), any(), any()); 153 } 154 155 @Test 156 public void testDuplicatedNotificationsNoInternetThenSignIn() { 157 final int id = 101; 158 final String tag = NetworkNotificationManager.tagFor(id); 159 160 // Show first NO_INTERNET 161 mManager.showNotification(id, NO_INTERNET, mWifiNai, mCellNai, null, false); 162 verify(mNotificationManager, times(1)) 163 .notifyAsUser(eq(tag), eq(NO_INTERNET.eventId), any(), any()); 164 165 // Captive portal detection triggers SIGN_IN a bit later, clearing the previous NO_INTERNET 166 mManager.showNotification(id, SIGN_IN, mWifiNai, mCellNai, null, false); 167 verify(mNotificationManager, times(1)) 168 .cancelAsUser(eq(tag), eq(NO_INTERNET.eventId), any()); 169 verify(mNotificationManager, times(1)) 170 .notifyAsUser(eq(tag), eq(SIGN_IN.eventId), any(), any()); 171 172 // Network disconnects 173 mManager.clearNotification(id); 174 verify(mNotificationManager, times(1)).cancelAsUser(eq(tag), eq(SIGN_IN.eventId), any()); 175 } 176 177 @Test 178 public void testDuplicatedNotificationsSignInThenNoInternet() { 179 final int id = 101; 180 final String tag = NetworkNotificationManager.tagFor(id); 181 182 // Show first SIGN_IN 183 mManager.showNotification(id, SIGN_IN, mWifiNai, mCellNai, null, false); 184 verify(mNotificationManager, times(1)) 185 .notifyAsUser(eq(tag), eq(SIGN_IN.eventId), any(), any()); 186 reset(mNotificationManager); 187 188 // NO_INTERNET arrives after, but is ignored. 189 mManager.showNotification(id, NO_INTERNET, mWifiNai, mCellNai, null, false); 190 verify(mNotificationManager, never()).cancelAsUser(any(), anyInt(), any()); 191 verify(mNotificationManager, never()).notifyAsUser(any(), anyInt(), any(), any()); 192 193 // Network disconnects 194 mManager.clearNotification(id); 195 verify(mNotificationManager, times(1)).cancelAsUser(eq(tag), eq(SIGN_IN.eventId), any()); 196 } 197} 198