Android 仪器测试和 Android Studio 中的单元测试之间的区别?

在 Android Studio 1.1 rc 中有 单元测试支持和 我想知道 Android 仪器测试和单元测试之间有什么区别

据我所知:
单元测试 对于测试不调用 Android 的代码非常有用 API 和 Android 仪器测试是相当集成的 测试 Android API 特定元素或 GUI 组件。

但是,如果您使用的框架,如 机器电学莫基托在您的 单元测试,如果我没有记错的话,你可以测试 Android 代码(不需要设备)。


这是正确的吗? 还是有更大的区别? 如果是的话,两者有什么用呢?

41329 次浏览

It seems to me that instrumentation testing is integration testing with the ability to control the life cycle and the events (onStart, onCreate etc) of the app.

Unit testing, as i understand it, is testing a Unit (eg Class) for its data and behavior.

For example, say you have a game: this game runs on an activity (main activity) and you have a character based on a Robot class, that has 2 methods (fire and move). You would test the main activity with an instrumentation test to see if it saves correctly when you leave the app, if it restores correctly when you restore it etc. and you would test Robot with a Unit test, to test its attributes and behavior.

Disclaimer: I'm not a java person, but i took interest in your question and i answered it based on a minor search online. You probably have to dig deeper into this to find a more detailed answer.

Unit tests isolate the component under test, and this is the reason why are often used together with Mocks frameworks as Mockito:because isolate the unit from their dependencies. Please notice what you say regarding the Android API is partially true, because there are also Instrumented Unit tests, namely Instrumentation is part of the Junit package as well, and also the classes that extend TestCase as the class AndroidTestCase is part of the Junit package but allows the use of A)Context, that you can call with getContext(), and B)Resources that are part of the Android API! Also please consider AndroidTestCase is a base class and there are several other classes quite useful that extend this class. They test specifically Loaders, ContentProviders and even Services and also them have access to the Android API. so these classes provide JUnit testing framework as well as Android-specific methods. Now with Junit4 there is the ServiceTestRule that extends directly from Object and allow you easier to test a Service, although you cannot start an Intent directly inside this class.

Instrumentation tests they are also into the Junit package, but the control of the Android API is quite total because Instrumentation Tests are instantiated in the system before any application code is run, and to test you need to open the real application(emulator or a phone connected with USB). They access to android components(ex. click a button) and application life cycle, they are usually slower than Junit tests that extend TestCase( the ones examined above) the typical use is with ActivityInstrumentationTestCase2 that has a functional test approach, more user oriented.

EDIT: Regarding Roboelectric and Mockito, that are togheter with Espresso between the most popular testing frameworks at the moment(13 July 2016), Roboelectric allows you to run multiple tests in seconds instead of minutes, and this comes really handy in teams that have to run continuous tests, and are subject to continuous integration.

From the site of Robolectric:

An alternate approach to Robolectric is to use mock frameworks such as Mockito or to mock out the Android SDK. While this is a valid approach, it often yields tests that are essentially reverse implementations of the application code. Roboelectric allows a test style that is closer to black box testing, making the tests more effective for refactoring and allowing the tests to focus on the behavior of the application instead of the implementation of Android. You can still use a mocking framework along with Robolectric if you like.

Mockito that also can be used with Junit, is really used with the exception of when have to manage final classes, anonymous classes or primitive types.

UNIT TESTING

Unit tests that run on your local machine only. These tests are compiled to run locally on the JVM to minimize execution time. Use this approach to run unit tests that have no dependencies on the Android framework or have dependencies that mock objects can satisfy.

So basically, you run plain java code to test for example a content provider, database connections, input and output of methods. This doesn't run on Android. To run it you DON'T need a device.

INSTRUMENTATION TESTING

Unit tests that run on an Android device or emulator. These tests have access to Instrumentation information, such as the Context of the app under test. Use this approach to run unit tests that have Android dependencies which mock objects cannot easily satisfy.

So it mocks how the user will use the actual application, therefore you NEED a device (physical or emulator) to run it. It has access to views, activities, context, etc.

Reference: http://developer.android.com/tools/testing/testing_android.html

Unit Testing:

Often Unit tests are referred to as “local tests” or “local unit tests”. The main reason for this seems to be that you want to be able to run tests without a device or an emulator attached.

Unit tests cannot test the UI for your app without mocking objects such as an Activity.


Instrumentation tests:

Instrumentation tests run on a device or an emulator. In the background, your app will be installed and then a testing app will also be installed which will control your app, launching it and running UI tests as needed.

Instrumentation tests can be used to test none UI logic as well. They are especially useful when you need to test code that has a dependency on a context.


Ref link for example

Unit Testing

It Runs on the local machine only.

Instrumentation Test case

It Runs on the android device or emulator .if you check the test case it runs on emulator or android device

Android tests

[Test types]

The diagram of test types in Android world

Local Unit test: JUnit, Mockito, PowerMock
Instrumentation tests(a kind of functional tests): Espresso, Robolectric, Robotium

//Functional tests(Integration, UI)
src/androidTest/java


//Unit tests
src/test/java

[Run test via Command line]

[Test double types]

Unit tests focus on small portions of code (i.e. class-level methods) and provide basic validation that code is working as expected. Espresso tests provide basic validation that the UI is working as expected.