2017-08-08 9 views
0

Ich versuche, Mockito und TDD zu lernen.Mockito Test überprüfen, ob Bluetooth aktiviert ist

Ich habe Moderator mit Methoden:

@Override 
    public void startScanning() { 
     if (isLocationPermissionGranted() && isBluetoothEnabled()) { 
      mPresenterView.onStartScanBtnClick(); 
     } else if (!isBluetoothEnabled()) { 
      mPresenterView.displayDialogRequestingBluetooth(); 
     } else if (!isLocationPermissionGranted()) { 
      mPresenterView.displayDialogRequestingPermission(); 
     } 
    } 

    @Override 
    public boolean isLocationPermissionGranted() { 
     return false; 
    } 

    @Override 
    public boolean isBluetoothEnabled() { 
     return false; 
    } 

Frage ist, wie ich 2 Methoden, die auf dem Boden Mockito Roboelectric oder w/e mit testen.

@Before 
    public void setUp() { 
     MockitoAnnotations.initMocks(this); 

     mScanningPresenter = new ScanningPresenter(mView); 

     mockBluetoothAdapter = PowerMockito.mock(BluetoothAdapter.class); 
    } 



    @Test 
    public void shouldPassPowerMock() { 

     assertEquals(true, mockBluetoothAdapter != null); 
    } 

    @Test 
    public void shouldDisplayBluetoothRequestWhenDisabled() { 

     mScanningPresenter.startScanning(); 

     PowerMockito.when(!mockBluetoothAdapter.isEnabled()).thenReturn(false); 

     verify(mView).displayDialogRequestingBluetooth(); 
    } 

Ich habe PowerMock und erstellten Test sicher zu sein, es funktioniert ^^ und ich hinzufüge, Test, der zeigt, was ich tun wollen, aber nicht wissen, wie noch

Meine Idee ist, diese Schnittstelle Methoden als geschützte Methode in Presenter zu machen und MockingClass zu erstellen. Oder Erstelle einen separaten Interface-Helfer und spotte ihn.

Ich bin offen für jede saubere Lösungen/Vorschläge.

Antwort

1

Jedes Mal, wenn ich sehe, jemand Powermockito für ein neues Projekt zu verwenden, beginne ich denke sofort Padmes Worte Anakin in Episode 3:

padme vs anakin

Du wirst einen Weg nach unten kann ich nicht folgen

Es für Powermockito hier keine Notwendigkeit - nur gute alte Java und Mockito :-)

Sie haben Sie einige öffentliche Methoden in Ihrem Presenter, die wahrscheinlich in separate Klassen extrahiert werden sollten. Die besten Arten von Präsentatoren delegieren ihre Aktionen einfach an andere Klassen und manipulieren die Ansicht mithilfe von show-Methoden. Das ist die alleinige Verantwortung des Präsentators. Man könnte so etwas wie dies leicht tun:

class PermissionsChecker { 

    private final Context context; 

    PermissionsChecker(Context context) { 
     this.context = context; 
    } 

    public boolean isLocationPermissionGranted() { 
     if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) 
      return false; 
     if (context.checkSelfPermission(Manifest.permission.ACCESS_COARSE_LOCATION) == PackageManager.PERMISSION_GRANTED) 
      return false; 
     return true; 
    } 
} 

Dann:

class BluetoothAdapterWrapper { 

    private final BluetoothAdapter bluetoothAdapter; 

    BluetoothAdapterWrapper(BluetoothAdapater adapter) { 
     this.bluetoothAdapter = adatper; 
    } 

    public boolean isBluetoothEnabled() { 
     return bluetoothAdapter.isEnabled(); 
    } 
} 

Jetzt ist Ihr Moderator etwas wie folgt aussieht:

class ScanningPresenter { 

    private final ScanningView scanningView; 
    private final PermissionsChecker permissionsChecker; 
    private final BluetoothAdapterWrapper bluetoothAdapterWrapper; 

    ScanningPresenter(ScanningView scanningView, PermissionsChecker permissionsChecker, BluetoothAdapterWrapper bluetoothAdapterWrapper) { 
     this.scanningView = scanningView; 
     this.permissionsChecker = permissionsChecker; 
     this.bluetoothAdapterWrapper = bluetoothAdapterWrapper; 
    } 

    @Override 
    public void startScanning() { 
     if (isLocationPermissionGranted() && isBluetoothEnabled()) { 
      scanningView.onStartScanBtnClick(); 
     } else if (!isBluetoothEnabled()) { 
      scanningView.displayDialogRequestingBluetooth(); 
     } else if (!isLocationPermissionGranted()) { 
      scanningView.displayDialogRequestingPermission(); 
     } 
    } 

    @Override 
    public boolean isLocationPermissionGranted() { 
     return permissionsChecker.isLocationPermissionGranted(); 
    } 

    @Override 
    public boolean isBluetoothEnabled() { 
     return bluetoothAdapterWrapper.isEnabled(); 
    } 
} 

Sie jetzt feststellen, brauchen wir nicht einmal die öffentlichen Methoden auf dem Moderator - Sie können sie aus dem Vertrag des Moderators entfernen und sie privat machen oder sie vollständig loswerden, wenn Sie möchten.

Jetzt ist Ihr Test sieht ungefähr so ​​aus:

@Mock PermissionsChecker mockPermissionsChecker; 
@Mock BluetoothAdapterWrapper mockBluetoothAdapterWrapper; 
@Mock ScanningView mockScanningView; 

//system under test 
ScanningPresenter scanningPresenter; 

@Before 
public void setUp() { 
    MockitoAnnotations.init(this); 
    scanningPresenter = new ScanningPresenter(mockScanningView, mockPermissionsChecker, mockBluetoothAdapterWrapper); 
} 

@Test 
public void shouldDisplayBluetoothRequestWhenDisabled() { 
    //arrange 
    when(mockBluetoothAdapter.isEnabled()).thenReturn(false); 

    //act 
    mScanningPresenter.startScanning(); 

    //assert 
    verify(mockScanningView).displayDialogRequestingBluetooth(); 
} 
+0

Verdammt. Super gute Antwort. "Danke, mein Meister" – Esperanz0

Verwandte Themen