Najoua Mahi
Najoua Mahi

Reputation: 316

Android Robolectric Exception

I am facing a problem with Robolectric library. I am writing unit tests using Robolectric, it's working locally but when I merge my code, it crashes on pipeline(remotely). I am using 'org.robolectric:robolectric:4.0.2' It fails by only adding this line to my test class: @RunWith(RobolectricTestRunner.class)

And the exception is:

FAILED org.apache.tools.ant.BuildException Caused by: org.apache.maven.artifact.resolver.MultipleArtifactsNotFoundException

Upvotes: 9

Views: 6358

Answers (3)

Yamashiro Rion
Yamashiro Rion

Reputation: 1976

In my case the issue was (./gradlew -i -d testDebug printed it):

Caused by:
org.apache.maven.artifact.resolver.MultipleArtifactsNotFoundException: Missing:
----------
1) org.robolectric:android-all:jar:10-robolectric-5803371
...

Robolectric tried to fetch a dependency from the remote repository, but it couldn't.

As the output suggests, I have:

  1. Manually downloaded org.robolectric:android-all:jar:10-robolectric-5803371 jar from the Maven repository.
  2. Located it in /home/user/jars
  3. Installed Maven on my machine: sudo apt install maven
  4. Linked the jar with Robolectic: mvn install:install-file -DgroupId=org.robolectric -DartifactId=android-all -Dversion=10-robolectric-5803371 -Dpackaging=jar -Dfile=/home/user/jars/android-all-10-robolectric-5803371.jar

Now ./gradlew testDebug works fine.

Also check the issue on Github, maybe there will be some more useful information for you.

Upvotes: 3

Najoua Mahi
Najoua Mahi

Reputation: 316

As @Christian.D said, Robolectric tries to download dependencies from external repository, but we need that it uses internal one. Below the fix:

1) Create a custom RobolectricTestRunner:

public class CustomRobolectricRunner extends RobolectricTestRunner {

public CustomRobolectricRunner(Class<?> testClass) throws InitializationError {
    super(testClass);
}

static {
    RoboSettings.setMavenRepositoryId("my-nexus");
    RoboSettings.setMavenRepositoryUrl("your_custom_url");
}
}

2) Annotate your test class:

@Config(manifest = Config.NONE)
@RunWith(CustomRobolectricRunner.class)

Good coding!

Upvotes: 0

Christian.D
Christian.D

Reputation: 949

I had the same issue: Robolectric was working fine locally, but once pushed to Jenkins the gradle task to execute the tests fails.

You can execute the gradle task to run the tests with -i -d flags to see more debug output.

./gradlew -i -d test

For me this revealed that Jenkins was unable to download Robolectric dependencies:

13:58:43  13:58:42.904 [DEBUG] [TestEventLogger] com.my.package.Test > my_test_case STANDARD_ERROR
13:58:43  13:58:42.904 [DEBUG] [TestEventLogger]     Downloading: org/robolectric/android-all/9-robolectric-4913185-2/android-all-9-robolectric-4913185-2.jar from repository sonatype at https://oss.sonatype.org/content/groups/public/

I could solve it by telling gradle to use our corporate proxy when running on Jenkins. One way to achieve this would be to add the following to your gradle.properties:

systemProp.http.proxyHost=http://proxy.host
systemProp.http.proxyPort=3128
systemProp.https.proxyHost=http://proxy.host
systemProp.https.proxyPort=3128

---- EDIT ----

Actually I found a cleaner solution for my use case then configuring a proxy: Robolectric offers a way to configure the repository it uses during runtime (see http://robolectric.org/configuring/). This way I was able to tell it to use our corporate repository.

android {
  testOptions {
    unitTests.all {
      systemProperty 'robolectric.dependency.repo.url', 'https://local-mirror/repo'
      systemProperty 'robolectric.dependency.repo.id', 'local'
    }
  }
}

Upvotes: 5

Related Questions