26

I have created a dummy activity inside androidTest folder and declared that activity in AndroidManifest file in androidTest folder.

My basic intention is to test a reusable fragment by putting it into a dummy activity with a framelayout container.

AndroidManifest.xml inside androidTest folder

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    package="com.droid.test"
    android:versionCode="1"
    android:versionName="1.0">
    <uses-sdk
        android:minSdkVersion="18"
        tools:overrideLibrary="android.support.test.uiautomator.v18" />
    <instrumentation
        android:name="android.test.InstrumentationTestRunner"
        android:targetPackage="com.droid" />

    <application>
        <uses-library android:name="android.test.runner" />
        <activity
            android:name="com.droid.DummyActivityForTest"
            android:screenOrientation="portrait">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.DEFAULT" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>
</manifest>

My test class TestWidgets.java

public class TestWidgets extends ActivityInstrumentationTestCase2<DummyActivityForTest> {
    private AppCompatActivity mActivity;

    public TestWidgets() {
        super(DummyActivityForTest.class);
    }

    @Override
    public void setUp() throws Exception {
        super.setUp();
        mActivity = getActivity();
    }

    @Test
    public void testAddSpecializationClick() {
        onView(withId(R.id.widgets_rv)).perform(
                RecyclerViewActions.actionOnItemAtPosition(4, click()));
        Assert.fail("Not Implemented");
    }

When I run my test class its throwing below exception,

java.lang.RuntimeException: Could not launch activity
at android.support.test.runner.MonitoringInstrumentation.startActivitySync(MonitoringInstrumentation.java:373)
at android.test.InstrumentationTestCase.launchActivityWithIntent(InstrumentationTestCase.java:119)
at android.test.InstrumentationTestCase.launchActivity(InstrumentationTestCase.java:97)
at android.test.ActivityInstrumentationTestCase2.getActivity(ActivityInstrumentationTestCase2.java:104)
at com.practo.droid.home.TestWidgets.setUp(TestWidgets.java:48)
at junit.framework.TestCase.runBare(TestCase.java:132)
at junit.framework.TestResult$1.protect(TestResult.java:115)
at android.support.test.internal.runner.junit3.AndroidTestResult.runProtected(AndroidTestResult.java:77)
at junit.framework.TestResult.run(TestResult.java:118)
at android.support.test.internal.runner.junit3.AndroidTestResult.run(AndroidTestResult.java:55)
at junit.framework.TestCase.run(TestCase.java:124)
at android.support.test.internal.runner.junit3.NonLeakyTestSuite$NonLeakyTest.run(NonLeakyTestSuite.java:63)
at junit.framework.TestSuite.runTest(TestSuite.java:243)
at junit.framework.TestSuite.run(TestSuite.java:238)
at android.support.test.internal.runner.junit3.DelegatingTestSuite.run(DelegatingTestSuite.java:103)
at android.support.test.internal.runner.junit3.AndroidTestSuite.run(AndroidTestSuite.java:69)
at android.support.test.internal.runner.junit3.JUnit38ClassRunner.run(JUnit38ClassRunner.java:90)
at org.junit.runners.Suite.runChild(Suite.java:128)
at org.junit.runners.Suite.runChild(Suite.java:27)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
at org.junit.runner.JUnitCore.run(JUnitCore.java:115)
at android.support.test.internal.runner.TestExecutor.execute(TestExecutor.java:54)
at android.support.test.runner.AndroidJUnitRunner.onStart(AndroidJUnitRunner.java:240)
at android.app.Instrumentation$InstrumentationThread.run(Instrumentation.java:1879)
Caused by: java.lang.RuntimeException: Unable to resolve activity for: Intent { act=android.intent.action.MAIN flg=0x14000000 cmp=com.practo.droid/.DummyActivityForTest }
at android.app.Instrumentation.startActivitySync(Instrumentation.java:385)
at android.support.test.runner.MonitoringInstrumentation.access$201(MonitoringInstrumentation.java:90)
at android.support.test.runner.MonitoringInstrumentation$5.call(MonitoringInstrumentation.java:353)
at android.support.test.runner.MonitoringInstrumentation$5.call(MonitoringInstrumentation.java:350)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588)
at java.lang.Thread.run(Thread.java:818)

I don't have much experience in Android testing, somebody please help with some suggestions.

Kristiyan Varbanov
  • 2,439
  • 2
  • 17
  • 37
Sreedhu Madhu
  • 2,480
  • 2
  • 30
  • 40

2 Answers2

13

There are 2 APK generated during project building. First is APK with application and second APK contains test. If you put your activity in test folder it will be in second APK that is used for test and your application APK does not contains it. This is why you are receiving this error (because your application APK does not have such activity).

So the only way for you is to put your activity not in test folder but in sources. You can create several application variants (see details here), so when you are building your APK in production your dummy activity will not be included in it.

2

I already answered this question here and places a link to a simple project that implements it, so you can even see the complete source code for that :-) I'll copy my of the answer here, because it seems that I achieved your goal:

That's easy! In general, you should just put your resources under the src/androidTest/res folder. And that is! Then you can use it in your src/androidTest/java files. Yes, you can't use test layouts in your production APK, but you can use your test layouts in your test APK.

There're some problems that might confuse you. For instance autocompletion works well not so very often, but, anyway, it builds and works.

It's the complete test tree, so you can see that I have that activity inside the test project and don't pollute the main one :-) Feel free to ask questions if something is still wrong :-)

$ tree androidTest/
androidTest/
├── AndroidManifest.xml
├── java
│   └── ru
│       └── egslava
│           └── lib_phone
│               ├── MainActivityTest.java
│               ├── TestActivity.java
│               └── actions
│                   ├── HintViewAction.java
│                   ├── KeepHintViewAction.java
│                   └── SetTextViewAction.java
└── res
    ├── layout
    │   └── activity_main.xml
    └── values
        └── styles.xml

And, yes, I can't answer your particular question because on my side everything works and I can't see your complete project :-) I just want to say that it works and you definitely don't need to move your test activities to non-test projects. Feel free to ask questions / post the code :-)

Community
  • 1
  • 1
Slava
  • 1,314
  • 14
  • 28
  • 4
    A comment to the answer by @Slava. His code works, because there is no separate apk for android library. Thus his solution ends up with a single test apk and there is no main apk, thus PackageManager resolves activities correctly. – lumag Apr 18 '19 at 22:18
  • @Fabio I get 'Error: Module not specified' if I try and run his RxSwipeRefreshLayoutTestActivity in AndroidStudio as I do with my own test activity within an Android lib (ie using `apply plugin: 'com.android.library'`). Any ideas? – Ewan Jan 07 '20 at 11:02
  • @Fabio Your link is dead. Here is the [new link to a lib that does just that](https://github.com/JakeWharton/RxBinding/blob/master/rxbinding-swiperefreshlayout/src/androidTest/java/com/jakewharton/rxbinding4/swiperefreshlayout/RxSwipeRefreshLayoutTestActivity.java) – Mahozad Aug 05 '21 at 13:28