Home | History | Annotate | Download | only in shadows
      1 package com.xtremelabs.robolectric.shadows;
      2 
      3 import android.app.PendingIntent;
      4 import android.content.Context;
      5 import android.content.Intent;
      6 import android.location.Criteria;
      7 import android.location.GpsStatus.Listener;
      8 import android.location.Location;
      9 import android.location.LocationListener;
     10 import android.location.LocationManager;
     11 import android.os.Bundle;
     12 import com.xtremelabs.robolectric.Robolectric;
     13 import com.xtremelabs.robolectric.WithTestDefaultsRunner;
     14 import junit.framework.Assert;
     15 import org.junit.Before;
     16 import org.junit.Test;
     17 import org.junit.runner.RunWith;
     18 
     19 import java.util.*;
     20 
     21 import static android.location.LocationManager.GPS_PROVIDER;
     22 import static android.location.LocationManager.NETWORK_PROVIDER;
     23 import static com.xtremelabs.robolectric.Robolectric.shadowOf;
     24 import static junit.framework.Assert.*;
     25 import static org.hamcrest.core.IsEqual.equalTo;
     26 import static org.junit.Assert.assertSame;
     27 import static org.junit.Assert.assertThat;
     28 
     29 @RunWith(WithTestDefaultsRunner.class)
     30 public class LocationManagerTest {
     31     private LocationManager locationManager;
     32     private ShadowLocationManager shadowLocationManager;
     33 
     34     @Before
     35     public void setUp() {
     36         locationManager = (LocationManager) Robolectric.application.getSystemService(Context.LOCATION_SERVICE);
     37         shadowLocationManager = shadowOf(locationManager);
     38     }
     39 
     40     @Test
     41     public void shouldReturnNoProviderEnabledByDefault() {
     42         Boolean enabled = locationManager.isProviderEnabled(GPS_PROVIDER);
     43         assertFalse(enabled);
     44         enabled = locationManager.isProviderEnabled(NETWORK_PROVIDER);
     45         assertFalse(enabled);
     46         enabled = locationManager.isProviderEnabled("RANDOM_PROVIDER");
     47         assertFalse(enabled);
     48     }
     49 
     50     @Test
     51     public void shouldDisableProvider() {
     52         // No provider is enabled by default, so it must be manually enabled
     53         shadowLocationManager.setProviderEnabled(GPS_PROVIDER, true);
     54         shadowLocationManager.setProviderEnabled(GPS_PROVIDER, false);
     55         assertFalse(locationManager.isProviderEnabled(GPS_PROVIDER));
     56     }
     57 
     58     @Test
     59     public void shouldHaveListenerOnceAdded() {
     60         Listener listener = addGpsListenerToLocationManager();
     61         assertTrue(shadowLocationManager.hasGpsStatusListener(listener));
     62     }
     63 
     64     @Test
     65     public void shouldNotHaveListenerOnceRemoved() {
     66         Listener listener = addGpsListenerToLocationManager();
     67 
     68         locationManager.removeGpsStatusListener(listener);
     69 
     70         assertFalse(shadowLocationManager.hasGpsStatusListener(listener));
     71     }
     72 
     73     @Test
     74     public void shouldReturnEnabledProviders() throws Exception {
     75         shadowLocationManager.setProviderEnabled(NETWORK_PROVIDER, false);
     76         shadowLocationManager.setProviderEnabled(GPS_PROVIDER, false);
     77         shadowLocationManager.setProviderEnabled(LocationManager.PASSIVE_PROVIDER, false);
     78 
     79         assertTrue(locationManager.getProviders(true).isEmpty());
     80         assertThat(locationManager.getProviders(false).size(), equalTo(3));
     81 
     82         shadowLocationManager.setProviderEnabled(NETWORK_PROVIDER, true);
     83 
     84         List<String> providers = locationManager.getProviders(true);
     85         assertTrue(providers.contains(NETWORK_PROVIDER));
     86         assertThat(providers.size(), equalTo(1));
     87 
     88         shadowLocationManager.setProviderEnabled(GPS_PROVIDER, true);
     89         providers = locationManager.getProviders(true);
     90         assertTrue(providers.contains(NETWORK_PROVIDER));
     91         assertTrue(providers.contains(GPS_PROVIDER));
     92         assertThat(providers.size(), equalTo(2));
     93 
     94         shadowLocationManager.setProviderEnabled(LocationManager.PASSIVE_PROVIDER, true);
     95         providers = locationManager.getProviders(true);
     96         assertTrue(providers.contains(NETWORK_PROVIDER));
     97         assertTrue(providers.contains(GPS_PROVIDER));
     98         assertTrue(providers.contains(LocationManager.PASSIVE_PROVIDER));
     99         assertThat(providers.size(), equalTo(3));
    100     }
    101 
    102     @Test
    103     public void shouldReturnAllProviders() throws Exception {
    104         assertThat(locationManager.getAllProviders().size(), equalTo(3));
    105 
    106         shadowLocationManager.setProviderEnabled("MY_PROVIDER", false);
    107         assertThat(locationManager.getAllProviders().size(), equalTo(4));
    108     }
    109 
    110     @Test
    111     public void shouldReturnLastKnownLocationForAProvider() throws Exception {
    112         assertNull(locationManager.getLastKnownLocation(NETWORK_PROVIDER));
    113 
    114         Location networkLocation = new Location(NETWORK_PROVIDER);
    115         Location gpsLocation = new Location(GPS_PROVIDER);
    116 
    117         shadowLocationManager.setLastKnownLocation(NETWORK_PROVIDER, networkLocation);
    118         shadowLocationManager.setLastKnownLocation(GPS_PROVIDER, gpsLocation);
    119 
    120         assertSame(locationManager.getLastKnownLocation(NETWORK_PROVIDER), networkLocation);
    121         assertSame(locationManager.getLastKnownLocation(GPS_PROVIDER), gpsLocation);
    122     }
    123 
    124     @Test
    125     public void shouldStoreRequestLocationUpdateListeners() throws Exception {
    126         TestLocationListener listener = new TestLocationListener();
    127         locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, 1, 2.0f, listener);
    128         assertSame(shadowLocationManager.getRequestLocationUpdateListeners().get(0), listener);
    129     }
    130 
    131     @Test
    132     public void shouldKeepTrackOfWhichProvidersAListenerIsBoundTo_withoutDuplicates_inAnyOrder() throws Exception {
    133         TestLocationListener listener1 = new TestLocationListener();
    134         TestLocationListener listener2 = new TestLocationListener();
    135 
    136         locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, 1, 1, listener1);
    137         locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 1, 1, listener1);
    138 
    139         Set<String> listOfExpectedProvidersForListener1 = new HashSet<String>();
    140         listOfExpectedProvidersForListener1.add(LocationManager.NETWORK_PROVIDER);
    141         listOfExpectedProvidersForListener1.add(LocationManager.GPS_PROVIDER);
    142 
    143         locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, 1, 1, listener2);
    144         locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, 1, 1, listener2);
    145 
    146         Set<String> listOfExpectedProvidersForListener2 = new HashSet<String>();
    147         listOfExpectedProvidersForListener2.add(LocationManager.NETWORK_PROVIDER);
    148 
    149         assertEquals(listOfExpectedProvidersForListener1, new HashSet<String>(shadowLocationManager.getProvidersForListener(listener1)));
    150         assertEquals(listOfExpectedProvidersForListener2, new HashSet<String>(shadowLocationManager.getProvidersForListener(listener2)));
    151 
    152         locationManager.removeUpdates(listener1);
    153         assertEquals(0, shadowLocationManager.getProvidersForListener(listener1).size());
    154     }
    155 
    156     @Test
    157     public void shouldRemoveLocationListeners() throws Exception {
    158         TestLocationListener listener = new TestLocationListener();
    159         locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, 1, 2.0f, listener);
    160         locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 1, 2.0f, listener);
    161 
    162         TestLocationListener otherListener = new TestLocationListener();
    163         locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, 1, 2.0f, otherListener);
    164 
    165         locationManager.removeUpdates(listener);
    166 
    167         List<LocationListener> expected = new ArrayList<LocationListener>();
    168         expected.add(otherListener);
    169         assertThat(shadowLocationManager.getRequestLocationUpdateListeners(), equalTo(expected));
    170     }
    171 
    172     @Test
    173     public void shouldRemovePendingIntentsWhenRequestingLocationUpdatesUsingCriteria() throws Exception {
    174         Intent someIntent = new Intent("some_action");
    175         PendingIntent someLocationListenerPendingIntent = PendingIntent.getBroadcast(Robolectric
    176                 .getShadowApplication().getApplicationContext(), 0, someIntent,
    177                 PendingIntent.FLAG_UPDATE_CURRENT);
    178         Intent someOtherIntent = new Intent("some_other_action");
    179         PendingIntent someOtherLocationListenerPendingIntent = PendingIntent.getBroadcast(
    180                 Robolectric.getShadowApplication().getApplicationContext(), 0, someOtherIntent,
    181                 PendingIntent.FLAG_UPDATE_CURRENT);
    182 
    183         shadowLocationManager.setProviderEnabled(GPS_PROVIDER, true);
    184         shadowLocationManager.setBestProvider(LocationManager.GPS_PROVIDER, true);
    185         Criteria criteria = new Criteria();
    186         criteria.setAccuracy(Criteria.ACCURACY_FINE);
    187 
    188         locationManager.requestLocationUpdates(0, 0, criteria, someLocationListenerPendingIntent);
    189         locationManager.requestLocationUpdates(0, 0, criteria, someOtherLocationListenerPendingIntent);
    190 
    191         locationManager.removeUpdates(someLocationListenerPendingIntent);
    192 
    193         Map<PendingIntent, Criteria> expectedCriteria = new HashMap<PendingIntent, Criteria>();
    194         expectedCriteria.put(someOtherLocationListenerPendingIntent, criteria);
    195         assertThat(shadowLocationManager.getRequestLocationUdpateCriteriaPendingIntents(), equalTo(expectedCriteria));
    196     }
    197 
    198     @Test
    199     public void shouldNotSetBestEnabledProviderIfProviderIsDisabled() throws Exception {
    200         shadowLocationManager.setProviderEnabled(GPS_PROVIDER, true);
    201         assertTrue(shadowLocationManager.setBestProvider(LocationManager.GPS_PROVIDER, true));
    202     }
    203 
    204     @Test
    205     public void shouldNotSetBestDisabledProviderIfProviderIsEnabled() throws Exception {
    206         shadowLocationManager.setProviderEnabled(GPS_PROVIDER, true);
    207         assertFalse(shadowLocationManager.setBestProvider(LocationManager.GPS_PROVIDER, false));
    208     }
    209 
    210     @Test
    211     public void shouldRemovePendingIntentsWhenRequestingLocationUpdatesUsingLocationListeners() throws Exception {
    212         Intent someIntent = new Intent("some_action");
    213         PendingIntent someLocationListenerPendingIntent = PendingIntent.getBroadcast(Robolectric.getShadowApplication().getApplicationContext(), 0,
    214                 someIntent, PendingIntent.FLAG_UPDATE_CURRENT);
    215         Intent someOtherIntent = new Intent("some_other_action");
    216         PendingIntent someOtherLocationListenerPendingIntent = PendingIntent.getBroadcast(Robolectric.getShadowApplication().getApplicationContext(),
    217                 0, someOtherIntent, PendingIntent.FLAG_UPDATE_CURRENT);
    218 
    219         shadowLocationManager.setProviderEnabled(GPS_PROVIDER, true);
    220         shadowLocationManager.setBestProvider(LocationManager.GPS_PROVIDER, true);
    221         shadowLocationManager.setProviderEnabled(NETWORK_PROVIDER, true);
    222 
    223         locationManager.requestLocationUpdates(GPS_PROVIDER, 0, 0, someLocationListenerPendingIntent);
    224         locationManager.requestLocationUpdates(NETWORK_PROVIDER, 0, 0, someOtherLocationListenerPendingIntent);
    225 
    226         locationManager.removeUpdates(someLocationListenerPendingIntent);
    227 
    228         Map<PendingIntent, String> expectedProviders = new HashMap<PendingIntent, String>();
    229         expectedProviders.put(someOtherLocationListenerPendingIntent, NETWORK_PROVIDER);
    230         assertThat(shadowLocationManager.getRequestLocationUdpateProviderPendingIntents(),
    231                 equalTo(expectedProviders));
    232     }
    233 
    234     @Test
    235     public void shouldStoreBestProviderCriteriaAndEnabledOnlyFlag() throws Exception {
    236         Criteria criteria = new Criteria();
    237         assertNull(locationManager.getBestProvider(criteria, true));
    238         assertSame(criteria, shadowLocationManager.getLastBestProviderCriteria());
    239         assertTrue(shadowLocationManager.getLastBestProviderEnabledOnly());
    240     }
    241 
    242     @Test
    243     public void shouldReturnNullIfBestProviderNotExplicitlySet() throws Exception {
    244         Criteria criteria = new Criteria();
    245         assertNull(locationManager.getBestProvider(null, false));
    246         assertNull(locationManager.getBestProvider(null, true));
    247         assertNull(locationManager.getBestProvider(criteria, false));
    248         assertNull(locationManager.getBestProvider(criteria, true));
    249     }
    250 
    251     @Test
    252     public void shouldThrowExceptionWhenRequestingLocationUpdatesWithANullIntent() throws Exception {
    253         try {
    254             shadowLocationManager.requestLocationUpdates(0, 0, new Criteria(), null);
    255             Assert.fail("When requesting location updates the intent must not be null!");
    256         } catch (Exception e) {
    257             // No worries, everything is fine...
    258         }
    259     }
    260 
    261     @Test
    262     public void shouldThrowExceptionWhenRequestingLocationUpdatesAndNoProviderIsFound() throws Exception {
    263         Intent someIntent = new Intent("some_action");
    264         PendingIntent someLocationListenerPendingIntent = PendingIntent.getBroadcast(Robolectric.getShadowApplication().getApplicationContext(), 0,
    265                 someIntent, PendingIntent.FLAG_UPDATE_CURRENT);
    266         Criteria criteria = new Criteria();
    267         criteria.setAccuracy(Criteria.ACCURACY_FINE);
    268         try {
    269             shadowLocationManager.requestLocationUpdates(0, 0, criteria, someLocationListenerPendingIntent);
    270             Assert.fail("When requesting location updates the intent must not be null!");
    271         } catch (Exception e) {
    272             // No worries, everything is fine...
    273         }
    274     }
    275 
    276     @Test
    277     public void shouldThrowExceptionIfTheBestProviderIsUnknown() throws Exception {
    278         Criteria criteria = new Criteria();
    279         criteria.setAccuracy(Criteria.ACCURACY_FINE);
    280         try {
    281             shadowLocationManager.setBestProvider("BEST_ENABLED_PROVIDER", true);
    282             Assert.fail("The best provider is unknown!");
    283         } catch (Exception e) {
    284             // No worries, everything is fine...
    285         }
    286     }
    287 
    288     @Test
    289     public void shouldReturnBestCustomProviderUsingCriteria() throws Exception {
    290         Criteria criteria = new Criteria();
    291         Criteria customProviderCriteria = new Criteria();
    292 
    293         // Manually set best provider should be returned
    294         ArrayList<Criteria> criteriaList = new ArrayList<Criteria>();
    295         customProviderCriteria.setAccuracy(Criteria.ACCURACY_COARSE);
    296         criteriaList.add(customProviderCriteria);
    297         shadowLocationManager.setProviderEnabled("BEST_ENABLED_PROVIDER_WITH_CRITERIA", true, criteriaList);
    298         assertTrue(shadowLocationManager.setBestProvider("BEST_ENABLED_PROVIDER_WITH_CRITERIA", true));
    299         criteria.setAccuracy(Criteria.ACCURACY_COARSE);
    300         criteria.setPowerRequirement(Criteria.NO_REQUIREMENT);
    301         assertThat("BEST_ENABLED_PROVIDER_WITH_CRITERIA", equalTo(locationManager.getBestProvider(criteria, true)));
    302         assertTrue(shadowLocationManager.setBestProvider("BEST_ENABLED_PROVIDER_WITH_CRITERIA", true));
    303         assertThat("BEST_ENABLED_PROVIDER_WITH_CRITERIA", equalTo(locationManager.getBestProvider(criteria, false)));
    304         assertThat("BEST_ENABLED_PROVIDER_WITH_CRITERIA", equalTo(locationManager.getBestProvider(criteria, true)));
    305     }
    306 
    307     @Test
    308     public void shouldReturnBestProviderUsingCriteria() {
    309         Criteria criteria = new Criteria();
    310 
    311         shadowLocationManager.setProviderEnabled(LocationManager.GPS_PROVIDER, false);
    312         criteria.setAccuracy(Criteria.ACCURACY_FINE);
    313         assertThat(LocationManager.GPS_PROVIDER, equalTo(locationManager.getBestProvider(criteria, false)));
    314 
    315         shadowLocationManager.setProviderEnabled(LocationManager.NETWORK_PROVIDER, false);
    316         criteria.setAccuracy(Criteria.ACCURACY_COARSE);
    317         assertThat(LocationManager.NETWORK_PROVIDER, equalTo(locationManager.getBestProvider(criteria, false)));
    318 
    319         criteria.setPowerRequirement(Criteria.POWER_LOW);
    320         criteria.setAccuracy(Criteria.ACCURACY_FINE);
    321         assertThat(LocationManager.NETWORK_PROVIDER, equalTo(locationManager.getBestProvider(criteria, false)));
    322     }
    323 
    324     @Test
    325     public void shouldReturnBestDisabledProvider() throws Exception {
    326         shadowLocationManager.setProviderEnabled("BEST_DISABLED_PROVIDER", false);
    327         shadowLocationManager.setBestProvider("BEST_DISABLED_PROVIDER", false);
    328         shadowLocationManager.setProviderEnabled("BEST_ENABLED_PROVIDER", true);
    329         shadowLocationManager.setBestProvider("BEST_ENABLED_PROVIDER", true);
    330 
    331         assertTrue(shadowLocationManager.setBestProvider("BEST_DISABLED_PROVIDER", false));
    332         assertThat("BEST_DISABLED_PROVIDER", equalTo(locationManager.getBestProvider(null, false)));
    333         assertThat("BEST_ENABLED_PROVIDER", equalTo(locationManager.getBestProvider(null, true)));
    334     }
    335 
    336     @Test
    337     public void shouldReturnBestEnabledProvider() throws Exception {
    338         shadowLocationManager.setProviderEnabled("BEST_ENABLED_PROVIDER", true);
    339 
    340         assertTrue(shadowLocationManager.setBestProvider("BEST_ENABLED_PROVIDER", true));
    341         assertFalse(shadowLocationManager.setBestProvider("BEST_ENABLED_PROVIDER", false));
    342         assertThat("BEST_ENABLED_PROVIDER", equalTo(locationManager.getBestProvider(null, true)));
    343         assertNull(locationManager.getBestProvider(null, false));
    344     }
    345 
    346     @Test
    347     public void shouldNotifyAllListenersIfProviderStateChanges() {
    348         TestLocationListener listener = new TestLocationListener();
    349         locationManager.requestLocationUpdates("TEST_PROVIDER", 0, 0, listener);
    350         shadowLocationManager.setProviderEnabled("TEST_PROVIDER", true);
    351         assertTrue(listener.providerEnabled);
    352         shadowLocationManager.setProviderEnabled("TEST_PROVIDER", false);
    353         assertFalse(listener.providerEnabled);
    354     }
    355 
    356     @Test
    357     public void shouldRegisterLocationUpdatesWhenProviderGiven() throws Exception {
    358         shadowLocationManager.setProviderEnabled(GPS_PROVIDER, true);
    359         shadowLocationManager.setBestProvider(LocationManager.GPS_PROVIDER, true);
    360 
    361         Intent someIntent = new Intent("some_action");
    362         PendingIntent someLocationListenerPendingIntent = PendingIntent.getBroadcast(Robolectric.getShadowApplication().getApplicationContext(), 0,
    363                 someIntent, PendingIntent.FLAG_UPDATE_CURRENT);
    364         locationManager.requestLocationUpdates(GPS_PROVIDER, 0, 0, someLocationListenerPendingIntent);
    365 
    366         assertThat(shadowLocationManager.getRequestLocationUdpateProviderPendingIntents().get(someLocationListenerPendingIntent),
    367                 equalTo(GPS_PROVIDER));
    368     }
    369 
    370     @Test
    371     public void shouldRegisterLocationUpdatesWhenCriteriaGiven() throws Exception {
    372         shadowLocationManager.setProviderEnabled(NETWORK_PROVIDER, true);
    373         shadowLocationManager.setBestProvider(LocationManager.NETWORK_PROVIDER, true);
    374         Criteria criteria = new Criteria();
    375         criteria.setAccuracy(Criteria.ACCURACY_COARSE);
    376 
    377         Intent someIntent = new Intent("some_action");
    378         PendingIntent someLocationListenerPendingIntent = PendingIntent.getBroadcast(Robolectric.getShadowApplication().getApplicationContext(), 0,
    379                 someIntent, PendingIntent.FLAG_UPDATE_CURRENT);
    380         Criteria someCriteria = new Criteria();
    381         someCriteria.setAccuracy(Criteria.ACCURACY_COARSE);
    382         locationManager.requestLocationUpdates(0, 0, someCriteria, someLocationListenerPendingIntent);
    383 
    384         assertThat(shadowLocationManager.getRequestLocationUdpateCriteriaPendingIntents().get(someLocationListenerPendingIntent),
    385                 equalTo(someCriteria));
    386     }
    387 
    388     private Listener addGpsListenerToLocationManager() {
    389         Listener listener = new TestGpsListener();
    390         locationManager.addGpsStatusListener(listener);
    391         return listener;
    392     }
    393 
    394     private static class TestLocationListener implements LocationListener {
    395         public boolean providerEnabled;
    396 
    397         @Override
    398         public void onLocationChanged(Location location) {
    399         }
    400 
    401         @Override
    402         public void onStatusChanged(String s, int i, Bundle bundle) {
    403         }
    404 
    405         @Override
    406         public void onProviderEnabled(String s) {
    407             providerEnabled = true;
    408         }
    409 
    410         @Override
    411         public void onProviderDisabled(String s) {
    412             providerEnabled = false;
    413         }
    414     }
    415 
    416     private class TestGpsListener implements Listener {
    417 
    418         @Override
    419         public void onGpsStatusChanged(int event) {
    420 
    421         }
    422     }
    423 }
    424