fauess
fauess

Reputation: 11

Android Instrumentation Test: Run code on host machine (not on device)

I'm trying to use Testcontainers in my Android instrumentation tests because I want to start a webserver before the tests which my app is using.

The problem is that all code that is executed in the instrumentation test runs on the Android device or emulator and thus it can't access the docker daemon running on my host machine which leads to this exception when I run the tests and try to start a container with Testcontainers library:

java.lang.IllegalStateException: Could not find a valid Docker environment. Please see logs and check configuration

So is it somehow possible to execute the code for starting Testcontainers on my machine instead of in the Android device/emulator or is there a good workaround for this scenario?

Here's an example class showing of what I'm trying to achieve:

import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation;
import static org.junit.Assert.assertTrue;

import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.testcontainers.containers.GenericContainer;
import org.testcontainers.containers.Network;
import org.testcontainers.containers.wait.strategy.Wait;
import org.testcontainers.utility.DockerImageName;
import android.webkit.WebView;
import androidx.test.ext.junit.runners.AndroidJUnit4;


@RunWith(AndroidJUnit4.class)
public class MyIntegrationTest
{

    private GenericContainer<?> webServer;

    @BeforeClass
    public void
    startServer() {

        Network network = Network.newNetwork();

        webServer = new GenericContainer<>(DockerImageName.parse("nginx:latest"))
        .withExposedPorts(80)
        .withNetwork(network)
        .withNetworkAliases("my-web-server")
        .withCommand("nginx", "-g", "daemon off;")
        .waitingFor(Wait.forHttp("/"));

        webServer.start();
    }



    @Test
    public void testMyWebApp() {

        // Load the web application in an Android WebView

        getInstrumentation().runOnMainSync(() -> {
            WebView webView = new WebView(getInstrumentation().getContext());
            webView.getSettings().setJavaScriptEnabled(true);
            webView.loadUrl("http://my-web-server/");
            assertTrue(webView.getTitle().contains("Welcome to nginx!"));
        });
    }



    @AfterClass
    public void stopServer() {
        webServer.stop();
    }

}

Upvotes: 1

Views: 259

Answers (1)

Code-Apprentice
Code-Apprentice

Reputation: 83557

The solution here is to write a separate script (bash or PowerShell, for example) that starts the webserver docker container and waits for it. Once the server starts, you can then launch your Android tests.

Upvotes: 0

Related Questions