2017-08-08 233 views
0

我正在尝试学习Mockito和TDD。Mockito测试检查是否启用蓝牙

我有演示用的方法:

@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; 
    } 

问题是如何测试使用的Mockito Roboelectric或瓦特/电子底部2点的方法。

@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(); 
    } 

我加入PowerMock和创建的测试,以确保它的工作^^和我加入测试,显示我想要做什么,但不知道我的想法是如何尚未

将此接口方法作为演示者中的受保护方法并创建MockingClass。或者创建单独的接口帮助器并对其进行嘲弄。

我对任何清洁解决方案/主张都抱有开放态度。

回答

1

每当我看到有人开始使用Powermockito一个新的项目,我马上在第3集想到帕德梅的话阿纳金:

padme vs anakin

你一起走下去的道路我不能遵循

没有必要为Powermockito这里 - 刚刚好老Java和:-)的Mockito

你在你的Presenter中有一些公开的方法,这些方法可能被提取到不同的类中。最好的演示者只需将他们的动作委托给其他类并使用show方法来操作视图。这是主讲人的单一责任。你可以很容易地做这样的事情:

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; 
    } 
} 

然后:

class BluetoothAdapterWrapper { 

    private final BluetoothAdapter bluetoothAdapter; 

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

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

现在你的演讲看起来是这样的:

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(); 
    } 
} 

您会注意到现在我们甚至不需要这些公共对演讲者的方法 - 你可以从演示者的合同中删除他们,并让他们私密或完全摆脱他们,如果你想。现在

您的测试看起来是这样的:

@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

该死。超级好的回应。 “谢谢你,我的主人” – Esperanz0